New in 13: Cloud & Webpage Construction
Two years ago we released Version 12.0 of the Wolfram Language. Here are the updates in cloud and webpage construction since then, including the latest features in 13.0. The contents of this post are compiled from Stephen Wolfram’s Release Announcements for 12.1, 12.2, 12.3 and 13.0.
WSTPServer: A New Deployment of Wolfram Engine (December 2020)
Our long-term goal is to make the Wolfram Language and the computational intelligence it provides as ubiquitous as possible. And part of doing this is to set up the Wolfram Engine which implements the language so that it can be deployed in as broad a range of computational infrastructure settings as possible.
Wolfram Desktop—as well as classic Mathematica—primarily provides a notebook interface to the Wolfram Engine, running on a local desktop system. It’s also possible to run Wolfram Engine directly—as a command-line program (e.g. through WolframScript)—on a local computer system. And, of course, one can run the Wolfram Engine in the cloud, either through the full Wolfram Cloud (public or private), or through more lightweight cloud and server offerings (both existing and forthcoming).
But with Version 12.2 there’s a new deployment of the Wolfram Engine: WSTPServer. If you use Wolfram Engine in the cloud, you’re typically communicating with it through http or related protocols. But for more than thirty years, the Wolfram Language has had its own dedicated protocol for transferring symbolic expressions and everything around them. Originally we called it MathLink, but in more recent years, as it’s progressively been extended, we’ve called it WSTP: the Wolfram Symbolic Transfer Protocol. What WSTPServer does, as its name suggests, is to give you a lightweight server that delivers Wolfram Engines and lets you communicate with them directly in native WSTP.
Why is this important? Basically because it gives you a way to manage pools of persistent Wolfram Language sessions that can operate as services for other applications. For example, normally each time you call WolframScript you get a new, fresh Wolfram Engine. But by using wolframscript -wstpserver with a particular “WSTP profile name” you can keep getting the same Wolfram Engine every time you call WolframScript. You can do this directly on your local machine—or on remote machines.
And an important use of WSTPServer is to expose pools of Wolfram Engines that can be accessed through the new RemoteEvaluate function in Version 12.2. It’s also possible to use WSTPServer to expose Wolfram Engines for use by ParallelMap, etc. And finally, since WSTP has (for nearly 30 years!) been the way the notebook front end communicates with the Wolfram Engine kernel, it’s now possible to use WSTPServer to set up a centralized kernel pool to which you can connect the notebook front end, allowing you, for example, to keep running a particular session (or even a particular computation) in the kernel even as you switch to a different notebook front end, on a different computer.
CloudExpression Goes Mainstream (December 2021)
You’ve got an expression you want to manipulate across sessions. One way to do this is to make the whole expression persistent using PersistentValue—or explicitly store it in a file or a cloud object and read it back when you need it. But there’s a much more efficient and seamless way to do this—that doesn’t require you to deal with the whole expression all the time, but instead lets you “poke” and “peek” at individual parts—and that’s to use CloudExpression.
We first introduced CloudExpression back in 2016 in Version 10.4. At that time it was intended to be a fairly temporary way to store fairly small expressions. But we’ve found that it’s a lot more generally useful than we expected, and so in Version 13.0 it’s getting a major upgrade that makes it more efficient and robust.
It’s worth mentioning that there are several other ways to store things persistently in the Wolfram Language. You can use PersistentValue to persist whole expressions. You can use Wolfram Data Drop functionality to let you progressively add to databins. You can use ExternalStorageUpload to store things in external storage systems like S3 or IPFS. Or you can set up an external database (like an SQL- or document-based one), and then use Wolfram Language functions to access and update this.
But CloudExpression provides a much more lightweight, yet general, way to set up and manipulate persistent expressions. The basic idea is to create a cloud expression that is stored persistently in your cloud account, and then to be able to do operations on that expression. If the cloud expression consists of lists and associations, then standard Wolfram Language operations let you efficiently read or write parts of the cloud expression without ever having to pull the whole thing into memory in your session.
This creates a cloud expression from a table of, in this case, polynomials:
This gives us the 5th part of the table:
We can reset it:
This gets the whole cloud expression:
But the important point is that getting and setting parts of the cloud expression don’t require pulling the expression into memory. Each operation is instead done directly in the cloud.
In a traditional relational database system, there’d have to be a certain “rectangularity” to the data. But in a cloud expression (like in a NoSQL database) you can have any nested list and association structure, and, in addition, the elements can be arbitrary symbolic expressions.
CloudExpression is set up so that operations you use are atomic, so that, for example, you can safely have two different processes concurrently reading and writing to the same cloud expression. The result is that CloudExpression is a good way to handle data built up by things like APIFunction and FormFunction.
By the way, CloudExpression is ultimately in effect just a cloud object, so it shares permission capabilities with CloudObject. And this means, for example, that you can let other people read—or write—to a cloud expression you created. (The data associated with CloudExpression is stored in your cloud account, though it uses its own storage quota, separate from the one for CloudObject.)
Let’s say you store lots of important data as a sublist in CloudExpression. CloudExpression is so easy to use, you might worry that you’d just type something like ce["customers"]=7 and suddenly your critical data would be overwritten. To avoid this, CloudExpression has the option PartProtection, which allows you to specify whether, for example, you want to allow the structure of the expression to be changed, or only its “leaf elements”.
Symbolic Webpage Construction (December 2021)
If you want to take a notebook and turn it into a webpage, all you need do is CloudPublish it. Similarly, if you want to create a form on the web, you can just use CloudPublish with FormFunction (or FormPage). And there are a variety of other direct-to-web capabilities that have long been built into the Wolfram Language.
But what if you want to make a webpage with elaborate web elements? One way is to use XMLTemplate to insert Wolfram Language output into a file of HTML etc. But in Version 13.0 we’re beginning the process of setting up symbolic specifications of full webpage structure, that let you get the best of both Wolfram Language and web capabilities and frameworks.
Here’s a very small example:
And here’s the webpage it produces:
The basic idea is to construct webpages using nested combinations of WebColumn, WebRow and WebItem. Each of these have various Wolfram Language options. But they also allow direct access to CSS options. So in addition to a Wolfram Language Background->LightBlue option, you can also use a CSS option like "border-right"->"1px solid #ddd".
There’s one additional critical feature: InterfaceSwitched. This is the core of being able to create responsive webpages that can change their structure when viewed on different kinds of devices. InterfaceSwitched is a symbolic construct that you can insert anywhere inside WebItem, WebColumn, etc. and that can behave differently when accessed with a different interface. So, for example
will behave as 1 if it’s accessed from a device with a width between 0 and 480 pixels, and so on. You can see this in action using CloudPublish
and then just resizing the window you use to view the result: