Telegram-Business" is a Telegram bot that connects customers to small-scale businesses. Users can either sign up to use the bot as business owners and create a catalog for their products or use it as customers looking to purchase something from businesses on the bot. It works a lot like the popular 'Whatsapp Business' platform.
In this article, I will teach you how to use Appsmith to build a product review tool for a Telegram bot. Think of this as a proof of concept of how Appsmith can help small businesses by automating some aspects of their businesses. More specifically, with this app, users can add reviews on products they've used to help others make wise decisions when purchasing, and business owners can take the feedback given to make their products more consumer-friendly.
If you want to see how I built the Telegram bot you can check this article I wrote about it here.
To follow along with the article steps, you should have the following setup:
The process starts by creating a new application on Appsmith, and designing the interface for the product review tool using the available widgets in the design area, as shown below:
This utilizes the rating widget for the star rating, the text widget to display the product description, image widget to show an image of the product, and input widget for the comment that the user may want to leave on the product as part of their review, and of course, a button widget to submit the review.
We also want users to see comments made by other people on the product, so we'll design a second portion of the interface right beneath this one, as shown below:
This portion consists of a text widget which describes the section "what others are saying", followed by the list widget, which has been emptied and contains only a text widget to display the comments by other users. It's empty at the moment so it seems bare, however, once the data kicks in it'll come to life. You can choose to add an outline to the input field to make it more visible as shown below:
We'll start by creating an API to fetch data to display on the list widget from the bot's database; which is hosted by Fauna which is a serverless database provider, that also provides us with a graphql API through which we can send queries directly to the database.
We will be querying the database via this GraphQL API from our Appsmith application. Head over to the "Queries/JS" section and choose to create a new "Blank API", and add the following details to this new API:
Once you're done your API should look like this:
You will observe that in the body of this API we make use of the "findProductByID" graphql query made available to us via FaunaDB.
Inside of this query we must specify a product id, namely the product id of the product that is to be reviewed, that way we can fetch the information about the product including the product image and description, which we can then display on our interface via the image widget and text widget.
id: "${appsmith.URL.queryParams.product_id}"
That is what this line does in the query, we fetch the product id from the Context object that Appsmith provides us with.
The Context object contains a number of properties of any Appsmith application that help us store and reference information about our application, for example, the famous "store" object is a part of the context object and we can use it to store information in our application's local store. Here's a list of items available in the Appsmith context object:
You can find out more about the context object here.
Meanwhile, the item of interest for us here is the "URL" object from the context object, which holds information about our application's URL, including the hostname, and query parameters amongst other things, as shown below:
This is important to us because we will be passing in information about the product to be reviewed and the user issuing a review as query parameters to our application url, namely the "product id" and the "user id" from the bot. This will make more sense when we integrate the application with the telegram bot.
Next, let's add another API that will fetch all the reviews on the given product. So head to the "Queries/JS" section again and choose to create a new API this time with the following details:
Here we send a query to the bot's database to fetch all reviews from the "Reviews" table that are associated with the given product's id, which is also gotten from the URL query parameter as with the previous API.
This API is what will handle the creation of new reviews which plays a vital role in our application since that's the main purpose of the application. This API unlike the rest utilizes a graphql mutation (also provided by the FaunaDB graphql API for the bot's database). Below are the details of this API:
As you can see in this mutation query, we reference the data from some of the widgets, including the rating widget, for the value of the ratings that are given. And the "input" widget, which holds the comment given by the user on the product. Also, observe that we fetch the user's telegram id (chat_id) from the URL to associate the new review with that particular user.
Next, we must connect the APIs we've created to the interface via some of the widgets. First, off we want the user to be able to send in a review to the database once they click on the "submit review" button, so to do that, we will open up the properties of the button by clicking on the settings icon next to it, and choose an OnClick action for the button.
Head over to the submit button widget and bring up the settings pane, and under the Actions section, choose the option to Execute a query and then select thesend_review` API from the list of options shown, as shown below:
Not only do we specify an "onClick" action, but we also specify an onSuccess action, which simply brings up a modal that displays a success message, like the one shown below:
This is a simple modal with just two Text widgets, so you can create one like that and link it to the onSuccess action as I have done.
Next, we must feed data to the list under the "What others are saying" section; click on the widget to bring up the settings for the list. Under the " items" option, add the following to load the data from our getReviews API:
This will load data from the query onto the list widget as a list of JSON objects. However, we must still specify what data goes where for each list item. In our case, we must specify what data from the "current object" goes to each list item's Text widget. Recall that each list item has a "text" widget in it, so for that text widget, we will specify its "Text" property to be the following:
Lastly, we must add data to the Image widget and the Text widget that holds the product's description. For the image, we'll set the "image" property to the following:
Here, I am calling the "getProduct" API, which we created earlier on, and fetching the data from the response of the API call. For the description text widget, we'll set the "text" property to something similar:
Now that we are done with this, we can deploy the application and fetch the URL. So I'll click on the Deploy button to deploy the application, wait for it to load up completely, then copy the URL from the browser.
As observed, the application currently has no data in it because necessary arguments for the APIs getProduct and getReviews are not yet present, namely:
If you recall, these two parameters were taken from Appsmith's URL context object, which holds information about the current URL of our application - including any query parameters that may be present.
This is important because I will be passing these two arguments as query parameters to our Appsmith application.
This brings me to my next stop, which is to implement some logic from the bot to help users who want to leave reviews access my application.
For this, I will send a message containing the link to our Appsmith application, along with the query parameters, which would contain the "ID" of the product they want to review and their user id on telegram (chat_id) to whoever is interacting with the bot.
Note: The code snippets shown below do not show the full implementation of my telegram bot; if you want to see how I built it, kindly refer to this article.
Typically, when users come to the bot, they get multiple options when viewing products in a catalog, as shown below:
As observed I have added a last option which allows them to Add Product Review, in order to handle that I wrote a handler function that will send back a message containing the Appsmith URL with the product id and their chat_id in the URL as query parameters. Observe:
The appsmith_url variable holds the URL for our deployed Appsmith application, and contains no parameters, so opening that would just display a "bare" version of the interface we designed. However, notice how i append the ?chat_id={chat_id} option along with the product_id={product_id} option to the URL before sending it.
That way the user gets a response that's customized to include their personal id and the id of the product they wish to review. As such, when they click on the URL our Appsmith APIs will be able to fetch the data they need from the context object and react accordingly. Here's what a typical response from the bot looks like:
Now when they click the link, it'll take them to the Appsmith tool we created but this time with data loaded in, as shown below:
This way, my users can also leave comments on the products, and see reviews on the product, further increasing the trust that they have in the platform and in small-scale business ventures.
I hope you enjoyed reading that!, this article has shown you how to use the Appsmith context tool as well as how to send GraphQL queries on Appsmith, via the API editor, and ultimately how to build a simple product review tool for any use case you might have.
I invite you to use what you've learned from this article to build more interesting versions of what I have built or even different tools if you wish, rest assured everything you need to fast-track your development is available to you on Appsmith.com. If you wish to see the code base for my bot you can find it on GitHub here.
Today, modern websites that use document-based data have provisions to view, manage and download these documents. Such documents can range from simple files showing budgets, tutorials, or even notes. With these features, application users can upload and manage files. While such features are nice to have, building an ideal solution to handle them are not feasible and can be time-consuming. Often developers find it hard to code PDF-viewers on their web apps because of dependency issues (libraries and frameworks), and when working with frontend frameworks — React, Vue.JS, etc. — configuration can get complicated.
When building apps on Appsmith, the in-built document widget takes care of some important functionalities related to managing documents. This widget supports multiple file extensions, such as .txt, .pdf, .docx and .xlsx among others. Documents can also be populated via APIs and URLs.
In this tutorial, we will learn what the document viewer widget is, and its applications. At the end, you will be able to fetch and display documents in Appsmith, and also learn to configure different properties that come with the widget.
The document viewer widget on Appsmith can be used to display a wide range of documents. This document widget has support for numerous file extensions of documents. Documents to be displayed can be of type: .pdf, .docx, .xlsx, .pptx, .ppt and .txt.
To get started using this widget:
.
Adding the widget will give a result similar to the image below:
Within the widget, you will notice there is a document being displayed. This document is being generated with the link in the Document Link property of the widget.
To display documents, you can either add links/URLs or connect a data source that can be connected to display documents. The document widget provides the option to download or print the displayed document.
Alternatively, a data source can be used to provide the documents.
The data source could be a database or an API pointing to the file you want to display.
The Connect Data button will take you to a page to add a data source.
Here you will see options for APIs and different databases.
In this tutorial, we will use the MongoDB database to supply our documents.
First, you will need to create a database on MongoDB (I will show you how to do this in the next section) and then link it to our application.
Select MongoDB from the datasource link
Here, I’ve renamed my data source to “Book Datasource.” Take note of the IP addresses; you will need to allowlist this when creating your MongoDB cluster to allow external access via Appsmith.
To get started with MongoDB, navigate your browser to MongoDB and click on Try free to create a user account.
After logging in, select your database plan and click on Create Cluster.
Next, set up security credentials to authorize access to the database.
Finally, allowlist the domains from Appsmith, click on the Finish and Close button, and click 'Go to Database' on the popup dialogue that appears.
On the new page that opens up, you will have your database and a cluster created for you.
On the cluster, click on the Browse Collections button.
You will get a page to manage the data stored in your database.
Select Add My Own Data to define our own database’s content. On the new page, select Insert document to add new documents to the database.
Our 'Collections' will contain two fields, namely: Name and Url, along with their corresponding values. Above I have a URL for a Javascript tutorial document. Click on the Insert button when done to add the new document.
Below, I have three documents in my database collection.
On the side pane, click on Database to navigate to the cluster. Click on the Connect button and select Connect with Mongodb Shell
Copy the selected area in the image below
Now that we are done setting up our database, we need to add it as a datasource to Appsmith. For this, you will need to navigate back to Appsmith and fill in the required fields.
Select Replica set for the connection type, paste the copied connection string into the host address field, and enter your database name. Under authentication, enter the username and password you defined when creating the cluster.
Click on test to check the validity of the datasource, then finally, click on Save. Click on the new query to create a query for the datasource.
Enter the name of the collection in the field provided and click on the Run button. You will get a response showing the database content. Click on Add new Widget and select Table on the left window pane. This will create a table widget with the database as its data source.
You can link this new widget to your document viewer widget.
To do this, open the document viewer widget option pane. Within the Document Link field, add the following moustache syntax
{{Table1.selectedRow.Url}}.
This will set the document to be displayed in the document viewer widget, to be the URL of any row you select from the table.
The document viewer widget has 3 properties: the Document Field, visible and Animate Loading properties. The visible field determines if the widget will be visible upon production while the latter controls the loading of the widget.
In the Filepicker widget, criteria can be set, which the document to be uploaded has to satisfy, else it would be rejected. Select and drag the file picker widget onto the workspace to add it.
Above is the file picker option pane. The label property is the text to be displayed on the widget. With this, you can also set the number of files to be uploaded, max size of the files, and allowed file types. Documents not meeting the predefined criteria will be rejected. Documents uploaded with the file picker widget can also be linked and displayed using the document viewer widget.
Click on the widget to upload a file.
You can either drag and drop files unto the widget to upload them, or you can browse your system directories for the files to be uploaded.
Here is a file I’ve added using the widget. Note that the file picker widget stores uploaded documents in the form of an array. To view your uploaded document, add the following mustache syntax to the document viewer widget document link property: {{FilePicker1.files[0].data}}. Here, the document at position zero is the first document which I added.
Above is an image showing the document uploaded using the file picker widget.
Documents can be sent to specific email addresses using the Appsmith SMTP email service. To do this, you will first need to do is to add SMTP integration. Navigate to datasources and select SMTP.
To be able to use this service, you will need to create an account with an SMTP provider. On the configuration page, add the host address, port and authentication credentials of your SMTP provider.
With SMTP setup, you can build a form to send the documents to an email address. To do this, add the form widget to your work environment.
Here is a form which will take the values of the name of the email and the file name of the document to be sent.
To send emails, create a new query using the configured SMTP service.
Here is the query screen. The from email property would take the email address you used to create your SMTP service, the To email(s) property can be bound to the input field of the form using the following moustache syntax: {{Input1.text}}. The subject would be: {{Input2.text}} and finally the attachment would be the file uploaded to the file picker widget. So use the moustache syntax: {{FilePicker1.files[0]}}.
Finally, you will need to bind this query to the submit button on the form to run it.
Here, I’ve added the query to the onClick event handler, and added a message to be displayed once the document has been sent. Clicking on the button will run the query and send the attached document to the email specified in the form.
We also covered using the file picker widget to upload files and send documents to specified email addresses. You can take a look at the tutorial here.
Building an online store with WooCommerce is incredibly easy. It allows you to upload your products, set up stock and downloadable products, and track orders and customer data.
And it is all free.
It makes sense that a lot of people use it and love it.
But getting reports out of it is hard sometimes. They have their default reporting tools, but they often don’t show all the information you need. And customizing it is incredibly complex.
A faster approach is to build a reporting dashboard using Appsmith. This allows you to create fully customized reports, and it’s easy to add new elements or edit the current ones.
Therefore, our goal for today is to make the WooCommerce and WordPress analytics even better. We will use Appsmith to read your database and build a sales reporting dashboard.
Along with the dashboard, we will explore many aspects of Appsmith and how to read external databases with it.
These are the things we are going to learn today:
Let’s get started!
You can check out the final app here. You can fork it and build your app using your database.
Before we start building, let’s walk through the main features of the app.
This button group allows you to select different timeframes in your queries. It allows you to check partial periods as well as completed periods quickly.
In addition, it is created in a way that you can easily extend it and add custom time selectors if you want (from X date to Y date).
The KPIs show you a quick overview of your primary metrics. You can use the ones we’ve created or create your metrics.
These charts allow you to quickly see orders for the selected period and how they compare to previous periods. This is the hardest part to implement in coding, but we have some excellent tips to make it much more manageable.
This map allows you to see your top performing countries, with labels on hover. It is quite an interesting element. It has some technical challenges as well, but it creates a useful visual element for online stores.
The product ranking allows you to see which are your top-performing products quickly. This is vital information for store owners, and you can get many insights from it.
Likewise, the top customers list shows your best customers and how much they are spending. You can use this information to reward them or find other customers with the same profile.
Now let's get to putting the UI together, but for that we need to plan what our app will look like.
Before coding your dashboard, you need a plan. There are many tools, from low-tech and reliable pen and paper to fancy design tools.
Another tool that might work well for you is Appsmith itself. You can use it as a prototyping tool. In this phase, you drag and drop the components you want to use on your page. Then you order them according to what makes the most sense for your decisions.
The wireframe is just like the final design in our demo, but with no data connections.
In addition to getting a feel of how your dashboard looks like, you can check two other points with your wireframe:
The first point is solved with some JS functions. The second one is solved with the DB connections.
Now that you know what your app looks like, it's time to check your data structures. Since we are going to read data from WordPress directly, you have three options:
The first option is the simplest. That's what we are going to do today. You can add your DB connection to Appsmith, and you are good to go.
The second option might work better depending on the data you want to load. If it is public data (which isn't the case for orders), this can be a quick solution, in particular, if you don't own the data source.
There are options to create custom API endpoints and authenticated requests. But this can get complex quite quickly. So make sure that this is the best option if you want to go for it.
The third option is an exciting one. In it, you can copy your database to another place. This allows you to pre-process your data if you want, reducing the stress on your main server. This might be a good option if you have too much data.
The downside is that you are always working with past data. Since you need to schedule this "mirroring" process, you are usually limited to doing it a couple of times per day.
You know the drill if you've worked with WordPress and WooCommerce before.
The data structures in WordPress are pretty hard to read, and WooCommerce makes it all the more complex.
This is where 'lookup tables' feature comes in.
They have been introduced in WooCommerce to solve performance issues. They are pre-processed versions of the most common WooCommerce queries you run, making it much, much faster. So, instead of checking the postmeta table, finding the post, then finding the user, you can look at the customer_lookup table, and it's all there.
There are many tables on your WordPress site, but we are going to use these in our demo:
You might have noticed that we have two additional tables in addition to the lookup tables. Let’s talk about them now.
It is common to plot all dates, even if you have no data in it when it comes to reporting. After all, you don’t want a chart that skips dates, giving you the false impression that there are only good days.
For this reason, we need to calculate all possible dates and times. You can do it with JS functions, but it can get messy. Therefore, it’s much easier to create a calendar table with all possible dates using a SQL function.
This allows you to select all dates and then join your desired data (revenue, for example). The same goes for the hous of the day. Instead of manually calculating them, get the table with times and LEFT JOIN your desired data.
Since we are dealing with pre-made tables, which we don’t control, we must double-check if all the data we need is there.
For example, if you have a KPI for sales goals, do you have this stored on your site? If not, you need to find a way to store it.
In our case, all our data is there. It’s just a matter of finding which tables to load where.
There are many approaches to this, but one that works well is to go through each component and describe what kind of data you need to populate it. From there, you can even list the tables involved.
Here is how you could do it for the demo dashboard:
Revenue - Sum of total sales from wp_wc_order_stats
Orders - Count of rows from wp_wc_order_stats
Average Ticket - Revenue / Orders
Orders completed chart
Get dates from the calendar or times
Left Join sum of total sales grouped by order date or time from wp_wc_order_stats
Get the sum of total sales from wp_wc_order_stats grouped by status
Get sum of total sales from wp_wc_order_stats
Left join country wp_wc_customer_lookup
Group by country
Products ranking
Get the sum of product revenue and count of orders from wp_wc_order_product_lookup grouped by product_id
Customers ranking
Get sum of order total from wp_wc_order_stats
Left join name from wp_wc_customer_lookup
Group by customer ID
As you can see, everything we need is there. Now it’s time to get our hands dirty.
Connecting the timeframe switchers
Let’s make the first component interactive. Drag and drop a button group to your page if you haven't already.
Next, add all options. You can create regular buttons (the main buttons) using the button type as simple, and you can create the “more” button using the menu type:
The menu type allows you to create sub-items for each menu item.
To mark a button as selected we are going to use the “disabled” property. You can set it as “true”, “false” or as the result of some JS code. This allows you to assign dynamic values to your buttons.
You can create a new JS object, then add this code in it:
This code just checks if the “slug” passed is the current button (stored in the appsmith.store.button variable). If it is the current button, it returns true, so the button is disabled. If it isn’t the current button, it returns false.
While you are at it, you can use this code to assign values to this “button” variable:
In this case, you could simply use the storeValue function directly. But since we need to re-run all our queries, it’s better to pass the button action to a function, and in it we can do it all. Here we can save the button value and run each of our queries again, to update data when the value has changed.
Now you just need to edit each of your buttons and add the disabled value you want, along with the “onclick” function to save the button value:
Once you have this, you can play around and click your buttons; they should turn on and off automatically.
You need one more adjustment. When the page loads, there is no value assigned to this button. But we need it in all our actions. You can create a function to run on page load to assign a default value to it:
Since this is an async function, you can click on the gear button next to it and enable “Run function on page load”:
The time limit is ready; now we need to use it. In this case, we use this function to generate the “where” part of all our queries. This is quite handy since you need to call this function whenever you have a time limit.
Now you are ready to load dynamic data! Let’s go through each of your components.
Loading data for the KPIs
As discussed earlier, the KPIs load the sum of all sales in the current period. You can do it with this SQL query:
SELECT SUM(total_sales) as "revenue", COUNT(order_id) as "orders" FROM `wp_wc_order_stats` WHERE {{utils.timeframe()[0]}}
Notice how we use the timeframe function with the current period as an argument.
This is the output for that query:
The revenue returns just a number though. Since we are using currency formatting in many different places, you can use this function in your JS object:
Then, you need to replace the current value in your KPI boxes.
This is the revenue:
That’s it! Your KPIs are ready.
Appsmith comes with some preset charts. But if you need custom charts, you can use any fusion chart you want.
You need to select the “custom chart” option and then pass the arguments as defined by fusion charts.
If you need multi-series data in a line format, you can use the msline chart. That’s what we use for the main sales chart.
This is what we use in the custom fusion chart field for that component:
The central aspect of this chart is that you need a setup, then your categories, and then your data series as arrays. In this case, we use the past data as the labels (since they have a complete series at all times), and we use current and past data in the datasets.
These datasets are created with 2 queries, but these queries just load a JS function. For the current data:
The entire function is quite long, but the entire logic can be summarized as follows:
Check if we load data from the calendar (dates) or the timetable
LEFT JOIN data from orders, grouped by the time restriction
Apply the time restriction in both queries
Return 2 queries (an array), one for the current selection and one for the past selection.
The orders by a status chart are created using a columns2d chart.
You can define your options such as axis names, palette colors, and captions in it.
Then, you need to pass the charts data. This is the query to load orders by status:
SELECT status as "label", COUNT(order_id) as "value" FROM `wp_wc_order_stats` WHERE {{utils.timeframe()[0]}} GROUP BY status
And this is the result:
You can see that the query is crafted with the chart in mind. Therefore, we need to return the label and value comuns, as per the widget.
Sales map chart
The map charts have options that significantly affect how your data is presented. Check it out:
You can pick the map type from a list of values. Some maps expect country IDs (from the fusion charts table), and some expect continents labels.
We call a function that does this mapping process for us to make things easier.
This is the SQL query to load data for the map charts:
This might seem complex, but this is what we are doing:
SELECT SUM of all revenue, SUM of all orders count, Country codes FROM
Wp_wc_order_stats (where you get all orders, sum of revenue, orders count)
LEFT JOIN wp_wc_customer_lookup (where you get the country code for your customers/orders)
GROUP BY Country code
Therefore, we get data from Wp_wc_order_stats (revenue) then we load the wp_wc_customer_lookup to know which country that order is from. Next, we group the result by country.
But this query generates a result that isn’t what the fusion charts component expects. Here is an example:
Therefore, we need to translate this data into their format. We can do it with array mapping. We use these 2 functions for that:
You can modify these functions to add more options (countries, continents) and manipulate data in other ways (for example, plot order count instead of revenue).
Either way, now, when you call utils.mappedCountries, you get all countries in the exact format you need.
A final touch is just creating chart labels in your desired format. Here is an example:
The product ranking is just a query that loads all orders within the timeframe selected. Then it groups all these orders by product ID, summing the order values and counting the number of orders.
It seems simple enough, but what about the ranking?
You can do it with some JS code, but you can include it in your SQL query if you want.
Here is how you can do it:
In this query, we set a variable (rownum), and for each row, your database adds one to it ( @rownum:=(@rownum+1) ).
The selection itself is similar to what we did before; the only adjustment is that we load the product name from the wp_posts table.
Then you can add this query to your table:
You can adjust the column names, and adjust the revenue to be set as:
This function converts the revenue value to currency.
The customers' ranking is very similar to the products ranking. The only difference is that we are using a list this time.
In this case, you can load the customer gravatar if you want (loading the gravatar image for their email). In our demo dashboard, we load placeholder images.
This is the query to load the customers ranking:
And you need to load its data in your list like this:
Similar to the table, you can reference the currentItem in your components to load data. For example, the revenue and orders field is set up like this:
Revenue: {{ utils.currencyFormat(currentItem.revenue) }} <br />Orders: {{ currentItem.orders }}
And that’s it! Your dashboard is ready.
Today we learned how to create a sales dashboard for WooCommerce sites. We discovered how to read data from WordPress and add it to different Appsmith widgets.
By the end of the day, you should be able to connect your WordPress site to Appsmith, creating your widgets. We didn’t cover some aspects of applications (such as security) for educational purposes, but this should be a great starting point.
We hope you’ve enjoyed it, and see you again next time!
Some things are fantastic together. 🍔🥤
In particular, REST APIs and Low code dovetail nicely.
Although APIs simplify development, they also demand a level of programming skill and technical ability. Low code frameworks like Appsmith can provide a visual layer on top of the API that empowers non-technical audiences and citizen developers to build client applications.
There is much value in simplifying the development process where we can. Low code works best for development projects where the problem domain is well understood and there are very few use cases. REST API clients are well suited to that extent - the API contract itself serves as a kind of blueprint for the client application. Take, for instance, the Brex APIs.
Brex offers several APIs that range from Onboarding and Payments to Teams and Transactions. Brex admins can plug into these APIs to build powerful workflows and custom automations. To demonstrate, we'll build an Appsmith dashboard that will connect to your Brex account.
In this tutorial, we'll create an Appsmith tool that leverages the Brex APIs to perform bulk operations on your Brex account. By uploading a CSV file, you'll be able to create credit cards, users, and vendors. These changes will be reflected in your Brex dashboard immediately. Our tool will also support terminating cards and deleting vendors.
As it is not intended for production use, this application doesn't attempt to be either complete or systematic. It is more like a demo project. Rather than serve as a proper software solution, the final application is meant to demonstrate what is possible using Appsmith and the Brex APIs.
For context, this tutorial depicts the reader as a fictional Brex customer in order to provide a frame of reference and bring meaning to the sample CSV files. Pretend that you are an outer space company that issues Brex credit cards to your colleagues. The cardholders have personal cards as well as other cards designated for expenses such as Equipment Repairs, Launch Services, and Telecom. You will also define fictional Vendors: General Atomics, Orbital Transport Services, Space Food Systems. Let's suppose you are building this application to automate a few back office operations. You have chosen to build it using Appsmith.
First, you'll want to sign into Appsmith and create a new application. Next, sign in to your Brex account and generate a user token with Read/Write permissions for Cards, Referrals, Users, and Vendors. Appsmith will use this token to authorize API calls.
To confirm that your token is working, you can perform a quick sanity check with curl:
COPYcurl --request GET 'https://platform.brexapis.com/v2/users/me' \
--header 'Authorization: Bearer <your-token>'
The response will resemble the following:
COPY{
"id": "cuuser...",
"first_name": "Michael",
"last_name": "Collins",
"email": "mcollins@example.com",
"status": "ACTIVE"
}
Alternatively, you can use Postman to test API calls. In fact, the Brex Developer workspace allows you to experiment with every endpoint documented in the Brex Developer Portal.
Consider using the Appsmith Echo API to spare production API calls.
COPY[POST] https://mock-api.appsmith.com/echo/post
While testing your Appsmith tool, sometimes you will need to invoke non-idempotent API endpoints such as Create card and Invite user. Instead of exercising the live endpoints, you can create an API datasource that relies on the Appsmith Echo API:
COPYfor(let i = 0; i < 5; i++) {
echo_post.run(onSuccess, onError, params);
}
To mock HTTP status codes and errors, you might try httpstat.us.
For testing user invites, I recommend a disposable email system like Mailinator or Temp Mail.
There's a companion repo that contains sample CSV files and supporting JavaScript code for this tutorial. You can also use Appsmith's Import-Export feature to migrate the demo application to your own account.
The base URL for all Brex APIs is https://platform.brexapis.com.
You should now have a datasource that we can use to create Queries.
New query objects will show in the left side panel, under QUERIES/JS. For example, here I've created a query for the Get current user endpoint:
Now, you can create new query objects from the brex-prod datasource. The following search box will appear when you click the + icon next to the QUERIES/JS menu option:
Going forward, we'll create several queries to support our application.
The Onboarding API allows you to refer your customers and personal contacts to Brex. You might use the Create referral endpoint as part of the Brex Referral Program.
Unlike the Get current user endpoint, Create referral is a POST endpoint that requires a JSON body.
Later on, we'll discuss this.params. For now, understand that it is possible to run the create_referral query object and pass parameters into it, like so:
COPYconst params = { referral_code, email, first_name, last_name };
return create_referral.run(params); // always return the promise
The Team API lets you manage users, departments, locations, and cards. For this example, we'll manage users and cards, starting with the Invite user endpoint, which allows you to invite a new team member as an employee. Through the dashboard, Brex admins can assign various role types to the employee, but team members created through this endpoint will bear the Employee role type by default.
Your invite_user query object will POST to /v2/users. The request body should match the following:
COPY{
"first_name": {{this.params.first_name}},
"last_name": {{this.params.last_name}},
"email": {{this.params.email}}
}
Under the Headers tab, be sure to generate a random string value for the Idempotency-Key:
Idempotency is well beyond the scope of this tutorial. But, in short, the idempotency key ensures that the API server will only process a non-idempotent request once.
For a moment, consider network interruptions that may cause downstream services (or even the application itself) to perform a retry. Without an idempotency, the server would attempt to process the same request again. The idempotency key helps the API server keep track of whether the operation was already performed or not.
Notice that the code to generate the Idempotency-Key includes a reference to Lodash: _.random(1000). Lodash, among other libraries, is built into the Appsmith platform, which is super handy.
Create Card
The create_card query object also requires an Idempotency-Key, and will POST to /v2/cards. The request body is:
COPY{
"owner": {
"type": "USER",
"user_id": {{this.params.user_id}}
},
"card_name": {{this.params.card_name}},
"card_type": "VIRTUAL",
"limit_type": "USER"
}
The Create card endpoint also accepts other parameters, card types, and limit types, so check out the developer docs. There's also a spend_controls parameter that allows you to define a spend limit for the card. This limit can be set to refresh each month, quarter, year, or never (for one-time use).
Terminate Card
We can also reference {{this.params...}} in the query object URL. For example, the terminate_card query object will POST to the Terminate card endpoint, which has a URI parameter, {{this.params.card_id}}:
COPY/v2/cards/{{this.params.card_id}}/terminate
The request body for terminate_card:
COPY{
"description": "demo",
"reason": "OTHER"
}
There are also other reason codes such as CARD_LOST, CARD_NOT_RECEIVED and FRAUD, but for this example, we'll stick with OTHER.
Note that the Idempotency-Key is not required, because card termination is idempotent by definition. In other words, terminating a card multiple times has the same effect as terminating a card once.
The Payments API allows you to initiate and manage payments and vendors from your Brex Cash account. We'll use the Create vendor endpoint as an example. In a production application, you would also include vendor payment information to enable ACH, wire, or cheque payments from your Brex Cash account. But, for this example, we'll omit the vendor's payment type. You can also add vendor payment information from the dashboard - How do I manage my vendors on Brex Cash?
Create Vendor
The create_vendor query object will POST to /v1/vendors. This endpoint requires an Idempotency-Key and the request body is:
COPY{
"company_name": {{this.params.company_name}}
}
Delete Vendor
The delete_vendor query object will send DELETE requests to /v1/vendors/{{this.params.vendor_id}}. There is no request body.
The following query objects will enable us to populate tables on page load. To ensure that Appsmith pulls the initial dataset each time, you can configure each query object to run on page load:
QueryEndpointget_cardsList cardsget_usersList usersget_vendorsList vendors
This option is located under the Settings tab inside the query object:
The goal of our app is to provide a user-friendly way to create Brex credit cards, vendors, invites, and referrals. In this section, we'll envision the page layout and breifly touch on a few key points. You'll use a drag/drop interface to build the UI. But, before we get started:
Now that our work is cut out, we'll begin creating each page.
Use the Appsmith widgets to create the following page to your ability. Note that the green Upload widget is a file picker, not a button.
Make sure the Data Format property is set to Text for each file picker:
The Users page has a Tabs widget with two tabs, one for invites and one for referrals. You can drag each Table widget into the appropriate tab.
The Referrals tab:
The Vendors page is almost identical to the Cards page. In fact, you can select every widget on the Cards page and copy/paste them onto the Vendors page. Of course, you'll also need to adjust the widget properties and table data.
Our application is starting to take shape. We now have an end-to-end skeleton system. Next, we'll incrementally add functionality to each page, incorporating the query objects we created earlier. We'll also learn about JS Objects, which allow us to define handler functions that we can bind to the page widgets.
Earlier, we created a few query objects to run on page load. Now, we'll use them to populate our table widgets. As stated in Running APIs on Page Load, "If we connect an API response to a widget, Appsmith automatically runs that API on page load..."
In effect, this means that binding {{get_cards.data.items}} to the Table Data property for tbl_cards will populate the table. However, for this tutorial, we only need the card id and card_name fields from each card. So, we'll write some additional code to remove the unwanted fields:
COPY// bind this to tbl_cards - Table Data property
get_cards.data.items
.filter(card => card.status == "ACTIVE") // only get ACTIVE cards
.map(card => ({ id: card.id, card_name: card.card_name }))
Likewise, we initialize tbl_invites and tbl_vendors:
COPY// bind this to tbl_invites - Table Data property
get_users.data.items
.filter(item => item.status == "INVITED") // only get INVITED users
.map(item => ({ email: item.email, name: `${item.first_name} ${item.last_name}` }))
// bind this to tbl_vendors - Table Data property
get_vendors.data.items.map(vendor => ({ id: vendor.id, company_name: vendor.company_name }))
In earlier versions of Appsmith, there was only support for writing small code snippets to data bind page widgets. But, Appsmith now supports JS Objects, which enable multi-line JavaScript code and reusable functions.
To create a new JS Object, click the + icon next to the QUERIES/JS menu option, and find the New JS Object option.
Create an object for each page: cards_object, users_object, and vendors_object.
Replace the contents of cards_object with the following code:
COPYexport default {
upload: () => {
showAlert('Cards created!', 'success');
}
}
We'll revisit this code shortly. At the moment, let's go back to the page editor and bind {{cards_object.upload()}} to the file picker's onFilesSelected event:
If you are curious, deploy the application and upload a file to the Cards page. You should receive a Cards created! notification.
The cards_object.upload method will leverage the create_card query to issue virtual cards. To follow along here, you'll need your Brex cuuser ID, which you can obtain by running the get_current_user query. Place your ID into a CSV file, formatted like this:
COPYcard_name,user_id
Michael Collins,cuuser...
Later on, we'll upload this file to the Cards page.
The following code will read lines from a CSV file, assuming that your file picker is called fp_cards:
COPY// get the first uploaded file
const csv_file = fp_cards.files[0];
// collect each line from the csv file
const csv_lines = csv_file.data.split("\n");
// omit csv header and blank lines
const rows = csv_lines.slice(1).filter(row => row.length > 0);
Simplified:
COPYconst rows = fp_cards.files[0].data.split("\n")
.slice(1).filter(row => row.length > 0);
To smoothen the discussion around asynchronous code and JavaScript promises, we'll be using a helper function called loop to iterate API calls. For reference, the full loop implementation is here, but we'll strictly focus on understanding its usage:
COPY// visit each row
return cards_object.loop({
collection: rows, // assign rows as the collection
onReadLine: () => {
// do this on every row
},
onEnd: () => {
// do this after the loop ends
}
})
The loop helper calls onReadLine once per row. On each loop iteration, we can pass card_name and user_id into create_card.run():
COPYonReadLine: (card_name, user_id) => {
// be sure to always return the promise,
// otherwise this will not behave as expected
return create_card.run({ card_name, user_id });
}
When the loop ends, we report the number of cards created successfully, and then call get_cards.run so that the new items appear in tbl_cards:
COPYonEnd: () => {
const count = appsmith.store.success_count;
if (count > 0) {
showAlert(`${count} cards created!`, "success");
}
get_cards.run();
}
Once you re-deploy the application and upload a valid CSV file, your card will show in the Brex dashboard, under Card > Manage cards:
Last, but not least, we have cards_object.terminate. Bind this method to btn_terminate_cards - onClick event:
COPYterminate: () => {
// clear variables
cards_object.reset();
// get comma-separated values from the textbox
const rows = txt_card_ids.text.split(",").map((id) => id.trim());
// visit each row, terminate card
return cards_object.loop({
collection: rows,
onReadLine: (card_id) => {
return terminate_card.run({ card_id });
},
onEnd: () => {
const count = appsmith.store.success_count;
if (count > 0) {
showAlert(`${count} cards terminated!`, "success");
}
get_cards.run();
},
});
}
The Users page involves many of the same techniques and concepts discussed earlier. However, there are two tables involved here. We'll need to refresh one of the tables, depending on whether the CSV file is intended for referrals or invites.
I should mention that an invite asks someone to join your Brex account as a team member, whereas a referral prompts someone to sign up for their own Brex account.
Creating an invite sends an email to the recipient:
On the other hand, creating a referral generates a personalized invite link to an onboarding flow. You can find your referral code at dashboard.brex.com/referrals. When the prospect visits their personalized link, they will see a pre-filled form containing data values sent through the Create referral API call:
When the CSV file is uploaded, we can inspect the header row to determine if the file contains referrals or not - referrals have a referral_code column while invites do not:
COPY// invites csv header: "first_name,last_name,email"
// referrals csv header: "referral_code,first_name,last_name,email"
let is_referral = rows[0].indexOf("referral_code,") == 0;
// ...
return is_referral
? users_object.createReferrals(rows)
: users_object.createInvites(rows)
For brevity, the full implementation code is shown here.
Something to note about the Create referral endpoint is that it returns the referral id and the referral_signup_url, but it does not return the applicant details (first name, last name, and email). Instead, the API consumer is expected to store and handle their own Brex referrals securely, as they contain sensitive information about the applicant.
Why do we need a data store?
At first glance, this might seem trivial. Perhaps, we don't need a referral data store. Maybe we could just create the referrals and then use the List referrals endpoint to load the recent items. However, the List referrals endpoint does not return any applicant information either.
So, by design, we need the data store to establish a link between the applicant details (passed into create_referral) and the referral id (returned from create_referral).
Without a data store, it's also not possible to seed tbl_referrals on page load. The List referrals endpoint doesn't return any applicant information, so we need to query the data store instead and then use that response data to populate tbl_referrals.
Implementing the data store
I'm using a serverless database (Fauna) to host the data store for this tutorial, but the type of database you use is unimportant. It is only important that the data store is accessible via a REST API, so that we can easily connect to the data source and create query objects:
QueryEndpointadd_referralgraphql.us.fauna.com/graphqlget_referralsgraphql.us.fauna.com/graphql
Fauna exposes a GraphQL API. Please see the the wiki for more details about this as it relates to add_referral and get_referrals.
Storing the referral data
Now that the data store is in place, we can persist the referral id and referral_signup_url along with the applicant information:
COPY// get response data and csv row
onSuccess: ({ id, referral_signup_url }, row) => {
// get applicant info from the row
const [referral_code, first_name, last_name, email] = row;
// store the referral data
add_referral.run({
id,
name: `${first_name} ${last_name}`,
email,
referral_signup_url,
});
},
Get referrals on page load
Also, remember to configure get_referrals to run on page load:
COPY// bind this to tbl_referrals - Table Data property
get_referrals.data &&
get_referrals.data.data &&
get_referrals.data.data.allReferrals.data
Implementation of the Vendors page is left as an exercise for the reader. Here are some things to keep in mind:
The full vendors_object implementation is here. You can also create multiple vendors by using the bulk upload tool in your Brex dashboard.
Thus far, we've only explored the happy path. If we return to the Cards page and upload cards.invalid-user-id.csv the create_card query will fail. Thankfully, Appsmith will handle this exception and display an error message.
But, imagine if you were to upload the following CSV file:
COPYcard_name,user_id
Space Mountain,invalid-user-id
Cargo Dragon,cuuser...
Planet Express,invalid-user-id
In this case, the API call would fail on Space Mountain and Planet Express, but the default error handling would not be able to detect which rows failed. To correct this, we'll need to implement the error handling ourselves.
During cards_object.loop(), whenever onReadLine fails, the onError function will trigger. We can implement onError to display a message:
COPYonError: ({ row }) => {
const [card_name] = row;
const message = `failed to create card "${card_name}"`;
showAlert(message, "error");
return message; // return message to the loop helper
}
The loop helper also keeps track of errors. There's a has_errors flag, which is a boolean that indicates when any errors have occurred. There is also an errors_arr collection where we store each error message for later display in tbl_errors.
The has_errors flag will determine if the red Icon Button is visible. Set its Visible property to {{appsmith.store.has_errors}}. Also bind its onClick handler to {{showModal("error_modal")}}. This button will launch a Modal that contains a table bound to {{appsmith.store.errors_arr}}:
The beauty of Appsmith is that you can migrate this application to your own workspace and repurpose it for your own needs. Here, we've touched on a few Brex API endpoints. We've also learned how to create an Appsmith dashboard that allows Brex admins to create and terminate Brex cards and refer and invite Brex users.
I encourage Brex admins to build and share custom Appsmith workflows that tap into the Brex APIs. There is much value in simplifying the development process where we can. Low code tools like Appsmith can provide practical advantages to Brex admins who need them, but they can also change the perspectives and attitudes of those who do not.
The views expressed in this post are my own and have not been reviewed or approved by my employer (Brex, Inc.).
A contact application is a database that collects and stores user contact data. The contact app is a widely used application, similar to the contact application on your mobile phone, that stores data such as user contact names, phone numbers, email addresses, etc. Businesses can use this application to manage their customers' information and store personal contact data.
This tutorial primarily focuses on integrating a contact API in Python using the Django Rest Framework. This application will have functionalities that allow users to create, edit, and delete contact data. While this goes on the backend of the application, we will create the interface of our application using Appsmith's pre-built UI widgets.
Appsmith is a powerful open-source low-code framework for creating internal tools with features such as pre-built UI widgets that connect to multiple data sources: APIs, databases, GraphQL, etc., with support for OAuth 2.0 and CURL.
Appsmith allows you to create web application interfaces with little or no code. You don't need to be a developer to create an application dashboard using Appsmith. Using Appsmith's drag-and-drop UI widgets, we will create a dashboard for our application.
We will begin by creating a virtual environment for our project. The essence of a virtual environment is to create a separate environment for all installed packages and dependencies.
The command below shows how to create a virtual environment in your terminal:
For Windows:
env\Scripts\activate
For Mac/Linux:
source env/bin/activate
Virtual environment activated!
Cloning a repository
Next, we will be cloning an already existing repository built with the Django Rest Framework. This repo contains a contact application with functionalities that allow users to create, edit, and delete contact data.
To clone the repo, run these lines of code in your terminal:
Once this is completed, we will be installing a couple of dependencies and packages required for this project using the pip These packages are already contained in your cloned requirements.txt file.
Run this command to create a requirements.txt file and install the packages:
Next, migrate the data to the database and create a superuser. To this by running the following commands:
Next, let's test this application locally, using the following command: python manage.py runserver
In your browser hit the endpoint http://127.0.0.1:8000/. You can also access the admin page using this URL http://127.0.0.1:8000/admin/
Great! Our application is running! 🎉
With our API up and running, the next phase of this project is creating an interface using Appsmith pre-built widgets and connecting these widgets to our data source (API). We will be doing this by writing some queries that will be implemented with the widgets.
Let’s dive in!
It takes a few minutes to connect to a datasource, and you can develop tools on the database of your choosing. You can either connect to a database, an API, or both. For this project, we will connect Appsmith to a deployed API using the API we earlier created. The deployed API can be accessed using this URL.
Add the URL of your deployed API and click on ‘run'.
Datasource successfully connected!
Now let’s get to work!
With Appsmith, you can build a fully customized interface with no code. Appsmith has many pre-built UI widgets such as tables, forms, buttons, boxes, images, and more, all available to help you create exciting applications.
Let’s begin! Firstly, let's create a table that will display our contact data.
Follow these steps:
Next, we will create a button widget that will be used to create contacts. When a user clicks this button, it navigates to another page that contains a form widget.
Drag and drop the button widget into the canvas.
In the label section, change the ‘submit’ label to 'create contact'. Next, edit the button widget, in the Events > onClick > Navigate to.
Under "Page Name or URL" type in 'Page 2'. By doing this, when we click on the "Create contact" button, it navigates us to a new page that will take us to the contact form.
Lastly, click on the "+" icon at the top left to add a new page.
This new page will contain a contact form that will be used to add a new contact, using input fields where users can enter the contact data they wish to create.
Let’s create a form using a form widget with these few steps:
By doing this, a connection will be created between the widget and the datasource.
Now let’s test out our widget to ensure that it's functioning. Firstly, on the contact dashboard, click on the "Create Contact" button. The button would redirect to another page that contains a contact form.
Fill out this form and hit the submit button. You will notice that contact details that are added through the form are displayed on our application dashboard.
So far, we have been able to create a form widget where users can create contacts, and these contacts will be displayed on our dashboard.
Great!
Asides creating contacts, contact applications also have features where users can edit contacts or delete contacts that are no longer needed. Let’s add the edit and delete contact buttons and write queries that will connect these buttons to our datasource.
In our application dashboard, add an edit button. This button will also be connected to our datasource. Let’s work on our edit button.
When you click on the edit button, it spins up a modal. We will edit this modal and add some queries to it to enhance its functionality. To do this:
Now you can edit a contact by clicking on the edit button and adding new data to replace the former contact data.
For the delete function, we simply repeat the same process as that of the edit button. However, the modal of the delete may differ. The Delete modal should appear like this:
Just as we did for the first modal, create a query that will connect the delete button widget to a data source.
Set the body property of your datasource to: {{Table1.selectedRow.id}}
Lastly, execute a query under Events > onClick. This button will query data from the deleted datasource you have created.
Our widgets and datasources are well implemented and functioning properly.
So far, we have done a great job. The last phase of this project will deploy our application. On the right section of the dashboard, click on 'Deploy'. You can also deploy this application by connecting to a Git repository.
Our application is deployed! 🎉
Finally, to test the work we have done so far. Try creating a new contact:
We will also test the delete button to ensure it's working as well:
Successful!
In this tutorial, we created an amazing user interface for our contact application with low code. I hope you had fun building!
Happy coding!🙂
Different organizations rely on admin panels to manage, read and mutate data stored in their database. An admin panel is a console used to control features configurations of an application and manage content in that application. Admins in most organizations use these to help control and manage content and provide security for the application. Anyone looking to handle applications or site functions easily will need to use an admin panel.
In this tutorial, you will learn how to set up a Redshift database and create and deploy an admin panel template built on Appsmith.
To set up your Redshift database: Navigate your browser to Redshift. Click on the 'Get started with Amazon Redshift' button. Sign in if you already have an account; else, create a new user account.
Next, you need to set up a new role for RedshiftDB. Click on Services in the top navigation, then IAM. Choose Roles from the left navigation panel and click on Create role. In the AWS Service group, choose Redshift. Next, choose Redshift - Customizable, then select Next: Permissions. On the Attach permissions policies page, scroll down and select AmazonS3FullAccess. Enter the role name and description, then click on Create role.
On the dashboard, click on ‘Create Cluster’ and enter your cluster name, cluster plan, admin username, and password in the form on the new page that opens up. Ensure to store your admin username and password as you will be using it to connect the database to the Appsmith app. You can finally click on the 'Create Cluster' button when you are done with that.
When the cluster is created, select the cluster and click on Actions; under the 'permissions' section, click on Manage IAM roles. When the management screen appears, select the IAM role you had created earlier, click on Associate IAM role, and click ‘Save Changes.’
With the newly created cluster, you can use a boiler template database. Click on the Query data button.
Select the newly created cluster in the left panel to use a cluster.
By default, Redshift creates a dev database that we will use in this tutorial. You can create your table data using the following command and run it to view your output.
Click on the 'save' button to save this query, enter the name of your query and finally, click save to store it.
To access the database's credentials, click on 'security credentials' in the dropdown menu on your user name at the top navigation bar. Click on 'Create new access key,' then download the key file in the access key.
After setting up the database, the next step is to create the panel on Appsmith.
The endpoint is your hostname, copy and paste it into the required field without the port number at the end. By default, the port number is 5429, but you can find this information in your endpoint.
With the Redshift data source connected, the data from the database can be displayed using a table. Navigate to the page and add a Table Component from the widgets section by dragging and dropping it onto the canvas. Next, open the table's property pane by clicking on the cogwheel icon on the table.
Before that, we need to set up a query for the data with the command:
COPY
COPY
SELECT firstname, lastname, total_quantity
FROM (SELECT buyerid, sum(qtysold) total_quantity
FROM sales
GROUP BY buyerid
ORDER BY total_quantity desc limit 10) Q, users
WHERE Q.buyerid = userid
ORDER BY Q.total_quantity desc;
Then on our page, we can get this data. In Appsmith, we use the mustache syntax {{}} to add Javascript. To get our query, we use {{Query1.data}}
Apart from reading the data to the table, you can use Appsmith to create and update functionalities.
To do this:
Drag the form widget onto the canvas from the widgets section and add the fields for the firstname, lastname, and total_quantity.
You will need to link the form to the database to add the new data with the form setup. You will need to write a query to collate the data from the form when the submit button is clicked and append it to the table. To do this, click on the cogwheel icon on the submit button. Then set the onClick to execute a database query and then click on create a query:
COPY
COPY
INSERT INTO users
('firstname', 'lastname', 'userid')
VALUES
('{{Input1.text}}', '{{Input2.text}}', '1');
INSERT INTO sales
('qtysold', 'salesid', 'listid', 'sellerid', 'buyerid', 'eventid', 'dateid')
VALUES
('{{Input3.text}}', '1', '1', '1', '1', '1', '1')
Here we entered the values of the input fields into the firstname, lastname, and qtysold. Also, I've set the id's to '1' for every entry; usually, you may use default values for this. You can now add new entries through the form to the table.
Apart from reading and creating table entries, we can also update and delete data from our table. You must first target a particular row and set it as the default value in the form's input fields to update the data.
Above, we set the Default Text for the input field to {{Table1.selectedRow.firstname}} to always get the data from the firstname column of the selected row in the input field. We repeat this step for lastname and total_quantity by entering {{Table1.selectedRow.lastname}} and {{Table1.selectedRow.total_quantity}} as their default text respectively. We need to add new functionality via a button to update the table. Add a button from the widgets pane and name the ‘Update’ button.
Next, create a new Javascript query for the on-click handler in the button option pane. For our new query to handle updates, we have the following:
COPY
COPY
update users
set firstname='{{Input1.text}}', lastname='{{Input2.text}}'
where firstname='{{Table1.selectedRow.firstname}}';
The query above checks for the row where the firstname corresponds to the selected row's firstname column value. It then replaces the firstname and lastname columns with the value of the input fields.
We can add another button called Delete to our form to do this.
Create a new query as follows:
COPY
COPY
delete from public.users where firstname = '{{Input1.text}}'
When executed at the click of the Delete button, this query checks the user's table and deletes the corresponding row, which has a firstname with its value corresponding to the selected data.
You can try out the query and observe that the selected row is removed when the 'Delete' button is clicked.
To deploy the Redshift panel template, click on the deploy button at the top right of the navigation bar. You can then make it publicly accessible or share it with specific individuals via email. The admin panel can be further modified with added functionalities such as user authentication for restricted access and email integrations to inform the admin when a change has occurred.
Proper feedback and community management is a significant part of building the organic reach of products, especially open source products. So, marketing teams might decide to build customized apps that contain valuable metrics. Products like Orbit allow us to get live data from our community forums to view them more concisely. In this tutorial, you will learn how to build an internal growth dashboard, where we’ll be able to display key metrics, including monitoring a Slack group and viewing existing members of the channel. The goal is to display specific growth metrics that enable better decision making in the marketing team.
First, we’ll be learning how to connect our Slack directly to Orbit, where we can view our information, activities, and members on their dashboard. Then, we’ll use Orbit’s REST API to view the data on our Appsmith dashboard.
This is useful in cases where we want to view our Slack data in a custom Appsmith app outside something like Orbit, mainly when the dashboard includes other external community data, not data from just the Slack channel.
We’ll [signup to Orbit] (app.orbit.love) and create our Orbit’s workspace:
Once we’ve created the workspace, we can now integrate our Slack community to orbit.
You can now open the Slack workspace you just connected with Orbit.
Go into your channel and open the Channel Details menu by clicking on the top-left channel name. Then, we’ll open the integration panel and click on “add apps.”
We’ll then see a bunch of apps where you’ll select Orbit.
The Orbit integration is now added to our #general channel! This automatically imports all messages and profiles (up to one year). Plus, it will listen for any new activities, including messages, thread replies, etc.
A message will automatically appear in the channel you just added, saying, “Orbit was added to #channel by you.”
To add the Orbit integration to more channels, we need to repeat the same steps or take advantage of the message shown above: Clicking on the name or icon of “Orbit” in that message will open a menu, from which you can add the integration to more channels with a click.
We’ve successfully connected Slack to orbit and can view all activities on our Orbit dashboard.
Setting Up Our Orbit API
Orbit offers RESTful APIs that we’ll use to pull our Slack data into our dashboard. The specific data pulling is the list of members from this Slack channel.
Here’s the endpoint:
app.orbit.love/api/v1{workspace_slug}/members
Note: You can can check the docs for more endpoints and use-cases.
You can find the workspace_slug under the workspace settings. It’s the text in bold below:
Let’s sign up to Appsmith and create our first app. On our first page we’ll add the container and text widgets to act as the header. Then, we’ll also add the list widget.
Now, we’ll go under QUERIES/JS dropdown on the left and create a new Datasource.
Set the API request to GET and add the endpoint. You’ll have to add your {workspace-slug} to the endpoint, as explained earlier. Once that’s done, we’ll click Edit Datasource, and it’ll take us to a page where we’ll add our header token.
Scroll down to the Authentication section of the page, down to the Bearer Token input, and add your Orbit’s API token. You can find that on the settings page. Note that you won’t add Bearer as a prefix, just the token. (that’ll be done automatically)
Let’s go back to our API datasource page and test it again
We now have everything functioning as it should, and the API provides the appropriate response. Look at the left and open a new page:
Once we select the list widget, we go to the left and see all related options. Under items, we’ll get the response preview by adding the name of the API: Orbit_Members.data.data.
{{Orbit_Members.data.data}}
Similarly, you’ll add an image widget inside the List item. On the right, we’ll use currentItem to refer to the current API in question. So it’ll be currentItem.attributes.avatar_url.
In the same vein, we add the name and email to the List item with {{currentItem.attributes.name}} and {{currentItem.attributes.email}}. If we do this correctly, we should have a similar screen to the one we have above.
First, we’ll create a new page called Member Details
We’re now going to add a button to each user that navigates us to a new page (Member Details). While navigating, we’ll save the user’s slug as a store value, and send it as a query param to the next page.
The aim is to use that slug to make another request on the new page. This request displays that particular user’s details. Under Member Details, we’ll name that request Member_Details and get our slug value from Appsmith.value.slug. This allows us pull the data for that single member that was selected on the Dashboard page.
Let’s go back to Member Details and display our data.
First, we add an image component to display the picture and use {{Member_Details.data.data.attributes.avatar_url}} to get our image URL from the Member_Details DataSource we created.
We also use {{Member_Details.data.data.attributes.location}} and {{Member_Details.data.data.attributes.avatar_email}} to display our location and email respectively.
Next, we’ll manually add other data to our dashboard. These include our Daily Active Users (DAU) and New Community Members.
There’s a sales report graph that helps us display our sales data.
In this case, we’re manually adding our data as an array.
Finally, we’ll hardcode other important data like churn rate, conversions, and our MRR.
Now that our Appsmith app is complete, what’s next? Deploying our shiny new app for other team members to use. Here’s the link to our application.
There’s also a tutorial below that shows you how to deploy with digital ocean. youtube.com/watch?v=6fitHGX2G4E&; youtu.be/6fitHGX2G4E
In this article, we’ve covered how to create a growth dashboard with Appsmith and Orbit‘s REST APIs. This shows us how to use low-code tools to optimize time and valuable resources when building internal tools in your company.
Orbit and Appsmith complement each other when it comes to monitoring community platforms like Slack, Discord, Discourse, etc. With Orbit, you get access to direct feedback and necessary information without spending engineering time building infrastructure from scratch. While Appsmith lets you focus on creating a visual dashboard with metrics, using minimal effort to implement and maintain.
Beyond using Orbit as a datasource, we can make use of custom REST APIs, Airtable, Supabase, Backendless, etc. Also, you can add other third-party integrations like intercom, email, or even add Zapier into your application. Appsmith can be customized into any form to fit your technical use-case.
If you have blockers or issues using Appsmith, you can always jump into our community Discord server to ask questions. Plus, you can connect with other Appsmith users.
Also, feel free to check other Appsmith tutorials using similar services like Cube, SnowflakeDB, Hasura, etc.
Information is the lifeline of any business, and to keep it alive and well, businesses have to transfer information to their various stakeholders like investors, bankers, suppliers, customers, government, etc. One of the simplest and the most effective ways of transferring information is using PDF files. These PDF files can be generated in different ways, but it involves lots of coding and configuration on your frontend and backend applications. To make this process easier on Appsmith (low-code framework to build internal tools), we created a workflow on n8n that uses APITemplate and simple webhooks.
This tutorial is a step-by-step guide on generating and exporting PDF files from data on your Appsmith application. Let's dive in!
The first step is to create an account on Appsmith. In this tutorial, I'll be using the cloud version of Appsmith, but you can always choose to use Appsmith locally or self-host it on your server.
Now, let's create a table from the mock database already provided on Appsmith.
Now let's bind this on a Table widget and then create a workflow to export it into a PDF file.
Following is what the application looks like now:
Excellent, our data is now ready. Now let’s create a workflow on n8n to generate PDF using APIs from APITemplate.io.
If you are new to these tools, the following is a quick intro to help you get started:
APITemplate.io: APITemplate helps auto-generate images and PDFs with Zapier, Integromat, N8n ow with a simple REST API.
Now let’s create a free account on APITemplate; you will be redirected to your dashboard after signing up. Navigate to the Manage Templates tab and create a new PDF template.
The template here is how you want your PDF to be organized this tutorial; I’ll be using the basic table template provided under the PDF template section.
Since our goal is to export the data on the Appsmith table, I’ve navigated to the HTML editor and removed all the unnecessary HTML content.
The idea is straightforward we send dynamic data from Appsmith onto the HTML template using a webhook, and APITemplate will generate a PDF file from the HTML.
Here’s how the HTML is added:
The item variable here holds all the data that will be updated from the webhook request on Appsmith.
We don't see any data here, as we did not have any workflow. So let's create on n8n!
n8n: n8n helps you to interconnect every app with an API in the world with each other to share and manipulate its data without a single line of code. It is an easy-to-use, user-friendly, and highly customizable service, which uses an intuitive user interface for you to design your unique workflows very fast.
I'll be using the cloud version of n8n for this tutorial. Note that you can also self-host n8n on your server.
Now, let's create the workflow:
Now copy the TEST URL, and create a new API on the Appsmith app by clicking on the + icon next to Queries and pasting the TEST URL in the request URL. Rename the query to generatePDF for a better naming convention.
Now navigate to the Body tab in the API request and paste the following JSON:
Here, we send the items data from the Table to the webhook using the moustache bindings.
Now, we can test this webhook by starting the workflow; here’s how it works:
Next, drag and drop a new APITemplate.io node and connect it to the webhook and use the following configuration:
This is where n8n sends data from Appsmith to APITemplate using a webhook.
Now, connect a new Respond to webhook node and set its respond with property to First incoming item property. This is how the complete workflow looks like:
Now click on execute the workflow and RUN the API on Appsmith; we should see a response with a downloadable PDF URL:
To improve the look and feel, we could create a new button and set its onClick property to run generatePDF query and bind the response to a text widget.
Here’s the complete workflow:
Alternatively, for PDF generation on Appsmith, we could also rely on other services like Zapier / Adobe.
If you’re interested in using a database not listed on our website as an integration, please let us know about it by raising a PR on Github, and we will do our best to include it at the earliest.
Join our growing community on Discord, and follow us on Youtube and Twitter to stay up to date.
Not every internal application is purely internal; sometimes, several organizations and teams need to have a way to automate their operations. For example, you might want to share your expense manager app with a financial advisor and other finance teams. Because there are multiple connections, having robust user authentication is crucial for such internal applications. But, adding an authentication layer to web applications is not straight forward task. The traditional approach is to have a form-based email-password authentication, then validating them with the backend using auth tokens and redirecting them onto the application. Sometimes users and developers prefer a faster way of using social authentication. This authentication allows users to log in to your app with their already set up credentials from their selected social sites.
Today, I’ll show you how you can add social authentication with Google to Appsmith applications without writing any piece of code. To do this, we will use Xano as the backend.
Before getting started, let me give you a quick introduction about Appsmith and Xano, in case you’re new here.
Appsmith is a low-code open-source framework to build internal applications, dashboards, crud apps, and many more. With Appsmith, it’s possible to create a fully functional and custom frontend in minutes. Connecting data sources with Appsmith takes a few minutes, and you can quickly build tools on top of the database of your choice.
Xano is one of the few no-code backend platforms that provide a comprehensive Database test environment, which allows you to easily switch between production and test data. Xano also provides API request history and easy ways to monitor CPU Usage and Database Record utilization.
Alright, now let’s get into it.
The first step is to create accounts on Xano and Appsmith. In this tutorial, I’ll use the cloud versions on both Appsmith and Xano.
Note: Since Appsmith is open-source, you can always use it locally or self-host it on your own servers using Docker.
After the Xano app is created, navigate to the API page in the dashboard, we’ll see two API groups; one is Default, and the other is google-oauth.
If you’re new to creating social auth keys on Google console, you can follow these steps from the documentation here.
Appsmith comes with a vast array of pre-built UI components: widgets. These can be fully customisable to help you build good-looking applications. For this application, I’ll keep the UI clean and simple, however, you can always add more to your applications based on your use-cases.
Now follow the below steps:
Here’s a screenshot of the form that’s built on Appsmith:
To initialize the authentication process, we’ll need to configure APIs on Appsmith from Xano, to do this follow the below steps:
There’s one last thing, we will need to set the button onClick action to JS and copy the following:
{{init.run(() => navigateTo(init.data.authUrl, {},'SAME_WINDOW'), () => {})}}
This code snippet will navigate to the redirectURI that’s requested from the init API call, which is obviously to the welcome page.
Note: The auth endpoint from Xano we used in this section is responsible for sending the user off to a Google webpage to authenticate. Once complete, the user will be redirected to where this request was initiated and then depending on your requirements, the user will go down the login, signup, or continue path.
Next, we’ll need to configure the continue flow to get details from the user and manage if the user is a first time user or an existing user.
To configure the continue workflow, navigate to the welcome page on Appsmith; this is where the user lands after the initialization is complete. First, let’s design the UI.
Next, create a new API by clicking on the + icon next to the datasource section and follow the below steps:
Now let’s test it out by clicking on the Login button from the login page, and we should successfully see the response on the continue API.
Here’s the GIF:
Awesome, we were now successfully able to finish the authentication process, now let’s bind the data onto the UI with JavaScript.
For this, set the text property on text widget to:
Welcome {{oauth_continue.data.name}}
This will show the username from the Google Account when the user is logged in.
To create a secure page on Appsmith with auth add a new page by clicking on the + icon next to the Pages. Next, drag and drop a TAB widget onto the canvas.
Now, open the property pane of the tab widget and rename the Tab names to logedin and notlogedin; under the Default Tab property, paste the following snippet:
This snippet will show logedin tab when the user has logged in and the notloggedin tab when there is no user. Here's how it works:
This is how we can achieve social authentication on the internal application! To see more details about other social providers, follow the Xano documentation here.
If you’re interested in using a database that is not listed on our website as an integration, please let us know about it by raising a PR on Github and we will do our best to include it at the earliest.
Join our growing community on Discord, and follow us on Youtube and Twitter to stay up to date.
Every project contains several moving parts. We developers call them features. They can be dashboards, performance overviews, a blog, or web pages that include forms. Features take time to develop from scratch. That can impact delivery and deadlines.
In this article, I want to create a metrics dashboard with Appsmith. I'll use API endpoints generated from Cube with a public dataset from the Museum of Modern Art (MoMA).
Here's what the end-product will look like:
I want to showcase how it would be more efficient for your team to have a tool to create custom dashboards for internal metrics. A huge bonus point is that it can be used by anyone, including non-devs in your team. This is where low-code tools come into play.
Appsmith is an open-source low-code platform that lets you create web applications like dashboards and admin panels by using drag-and-drop widgets. With Appsmith, you can connect multiple data sources like MySQL, MongoDB, REST API, Google Sheets, and perform CRUD operations.
I'll be using a hosted Cube deployment on Cube Cloud to get data from the Museum of Modern Art (MoMA) dataset.
You don't need to be a developer to create metrics dashboards using Appsmith. It comes with a set of drag-and-drop widgets for forms, charts, images, and more, that you can use in your application to enhance its functionalities.
A few of the benefits of Appsmith include:
However, keep in mind that despite all of its functionality, Appsmith can't compare to the customization level of a custom-built app.
Cube is an open-source analytics API platform that lets you connect with data sources and then access the data through an API. You can connect to data sources like MySQL, AWS Athena, and Google BigQuery, among others. It's agnostic for visualization tools, meaning you can connect to any front-end charting framework and build your own customized UI.
The Cube API lets you sort, group, and filter through the dataset itself. It acts as a centralized back-end metrics layer for any dataset. The multi-staging query system allows Cube to handle trillions of data points.
You're going to display a public dataset from the MoMA on the dashboard you're creating on Appsmith. The MoMA is one of the largest and most influential museums in the world, with around 300,000 books and catalogs, and more than a thousand periodic files.
This is how your dashboard will look:
You'll use db4free.net, a free database service, to upload and host the database. After uploading the data to the database, you'll connect to the database using Cube. You'll be able to integrate the API generated through Cube into the different widgets of Appsmith.
Once you clone the dataset, use the PHPMyAdmin or the cPanel of the database hosting service and import the data via CSV.
Now log in to your Cube account and click Create deployment. Give the deployment a name; the images in this example will use Appsmith Dashboard.
On the next screen, select MySQL from the data source list. If you're using some other data source like Google BigQuery or AWS Athena, select the option accordingly.
Now, just fill in your database credentials, and you're good to go!
Once you've generated the data schema of your dataset, you can create REST APIs.
Once you have created a deployment, you'll be redirected to the overview page of the deployment.
Copy the API endpoint and click How to connect your application to get the Authorization key.
And you're done creating Cube's API. It's time to move ahead with Appsmith to create your dashboard.
Log in to your Appsmith account, create a new application, and select Build with drag & drop.
Once you see an empty canvas, click the + button next to Datasources in the sidebar. Select Create new API.
You should see the following page:
For the URL, paste the REST API endpoint, and in the Authorization header, paste your API code. In the case of this tutorial, the REST API endpoint is https://fuchsia-shark.aws-eu-central-1.cubecloudapp.dev/cubejs-api/v1/load.
Pass the following JSON as a GET param:
In this code block, you're asking the REST API to return the top ten begin dates and display name. The rows are in descending order.
Once you start to get the data, you'll see a list of widgets on the right side of the page. Select Table from this list:
A table will appear in the canvas.
Repeat the previous step but with a different query. Just add another API data source with the following query:
This query will return the count of artists according to country.
Again, select Table from the widget list. Your canvas should look something like this:
In this example, I've experimented with different widgets and data customizations. I've added three more charts using this query.
This query will return the count of all artists with their begin date.
This query will return the gender breakdown of the complete dataset. I have used the data coming from this API in the pie chart.
This query will return the count of artists from each country listed in the dataset.
You can use this query with any widget to represent the data efficiently.
In this article, you learned how to create a metrics dashboard with Appsmith and Cube to display data from the public dataset from the Museum of Modern Art (MoMA). You now know how to use low-code tools to save time and money on development.
Check out the live example here and try adding some more widgets to your metrics dashboard with Appsmith.
I think Cube and Appsmith are a great match. With Cube, you focus on creating business value without wasting time and effort on maintaining infrastructure.
Appsmith lets you focus on creating business value with metrics dashboards with minimal effort to both create and maintain.
You can register for Cube Cloud right away, and check out Appsmith as well!
I'd love to hear your feedback about building metrics dashboards with Cube Cloud in the Cube Community Slack. Click here to join!
Until next time, stay curious, and have fun coding. Also, feel free to leave Cube a ⭐ on GitHub if you liked this article. ✌️
GraphQL is a query language for APIs and a server-side runtime for executing queries using the system you define for your data. It provides a complete and understandable description of the data in your API, gives clients the power to ask for exactly what they need and nothing more, makes it easier to evolve APIs over time, and enables powerful developer tools.
Today, developers spend a lot of time building internal applications, dashboards, and admin panels with GraphQL APIs as backend. But guess what? It’s now possible for you to write customizable applications with the ability to quickly prototype and deploy in a few minutes. With Appsmith, a low code app builder, you can build entirely customizable internal tools without spending too much time or effort.
In this blog, I am going to be building an e-commerce order management dashboard.
To build this app, we will connect Appsmith with a GraphQL API and build an interface that will fetch information from a database. We will use Hasura to create, manage, and customize GraphQL APIs.
Hasura is an open-source service that gives you production-grade GraphQL & REST APIs on your data instantly. It allows you to develop and deploy GraphQL APIs in minutes. At the core, Hasura helps you build APIs with a simple to use GraphQL composer and a GraphQL server that is stateless and blazing fast.
By the end of the tutorial, we will have a fully customizable e-commerce order management dashboard! Typically, such dashboards enable the app users to:
Note: We will be using data from Hasura Super App, which can be found here. You can directly migrate the data here to your Hasura instance in just a few steps listed here: Moving from local development to staging and going production with Hasura.
Alternatively, you can connect to the instance we created for you to test and play with GraphQL APIs on Appsmith. These details of the instance are disclosed in the next section :)
All right, let's dive in!
We will be connecting to the Hasura instance via the REST API datasource on Appsmith. For this, we will need the GraphQL API end-point and Admin Secret key from Hasura Dashboard. If you're using your instance, this is how your dashboard looks like, where you can copy the mentioned details.
If you want to know more about the data schema and customize the relations between tables, you can always use Hasura cloud explorer.
Now, let's quickly take a look at all the tables that are available on Hasura Super App Dashboard in brief:
Awesome, now that we had a glance at our tables, let's build the app! First up, we'll need an account on Appsmith Cloud. You can create it here for free if you don't have one. After we log in, we will be redirected to our dashboard to make a new Appsmith; this can be under any organization of your choice.
Now, to connect Hasura APIs, follow the below steps:
https://subtle-platypus-36.hasura.app/v1/graphql
content-type: application/jso
x-hasura-admin-secret: <YOUR_SECRET_KEY>
Now, we can test this GraphQL query by clicking on the RUN button to the top-right of the application; with this, we should see all the products list from the backend in the response body.
Following is the screenshot:
Here, inside the body pane, we write the GraphQL query to fetch all the products; this is similar to how we do it on a regular GraphiQL playground.
Now let's bind this data onto the table widget.
{{ getproducts.data.data.product }}
Doing a simple READ operation using Hasura's GraphQL API is easy now; let's look at how we can do a WRITE operation by building a form on Appsmith. Follow the below steps:
Following is a screenshot of how the form should look like:
Now, update the form names to the following to access them in the query:
You can update the widget names from the property pane by double-clicking on the existing one.
Now, add a new button, update its label to Add Product, and set its onClick property to "Run a query" and choose Create a new API. This will create a new API datasource under the datasources section. Now, follow the below steps to create a new query that lets us post new data onto PostgresDB on Hasura.
https://subtle-platypus-36.hasura.app/v1/graphql
Here, we have an object consisting of a query key that holds the GraphQL query and a variables key with all the variables that need to be posted to the database.
In the query, we have a mutation that lets us modify the server-side data. We'll send the object that references the data querying inside the mutation. The insert_product_one allows us to post one object to the database. Inside this query, we can add the attributes we need to post. Next, we've associated the variables to the object from the created UI input widgets. The .text on the input widget name helps us get the text written inside the input.
That's all, and our query is now ready! We can test this out by opening the form and creating a new product on our e-commerce store.
In this section, we will be showing some statistics on our dashboard; for this, let's drag and drop three stat box widgets onto the canvas. Following is a screenshot of how it looks like:
As we can see, these stat box widgets compute the total products, total categories, and unique brands. The data here is computed directly from the Hasura instance, using JavaScript. Following is how it works:
On the first stat box widget, select the text-widget and paste the following in the Text property:
This small JS code will return the array's length from the getproducts query, displaying the total products.
Similarly, update the other two stat box widgets with the following JS code:
To compute Total Categories, we use an IIFE function and filter the getproducts query using its category_display_name attribute :
To compute Unique Brands, we use an IIFE function and filter the getproducts query using its brand attribute :
There we go; we now have our dashboard up and running! Not just that, Appsmith allows us to create charts on top of Hasura data. Let's learn more about it in the next section.
To get started, let's rename the page as Recent Orders; the idea is to create a chart that shows daily sales. Drag and drop a new chart widget onto the page from the widgets section.
This will show you a column chart with some pre-defined data; let's update this by creating our new query that fetches all the sales data:
This query will return a bit complex JSON; we will see something like:
{ "data": { "order": [ { "order_products": [ { "product": { "order_products": [ { "quantity": 2 } ] }, "created_at": "2021-02-22T18:16:17.776779+00:00" } ] }, … }
Here, order_products are nested in an array; hence, to process this and put it on a chart widget, we create a new JS object, allowing us to write full code on Appsmith and utilize its widgets. Confused? Follow the below steps:
Here, we do a simple ordering using the _.compact method from lodash to aggregate the total number of sales done on a particular date. We return these in a special {x: value, y: value} format, which is accepted by the chart widget.
Now, let's head back to the chart widget and use this JS Object:
Update the series data property with the following:
{{JSObject1.myFun1()}}
Boom! There you go, we have all our sales aggregated based on the date on a beautiful chart widget. Following is how it looks like:
We also extended this app to show all the sales and orders on stat boxes and list widgets. Here's the link to the complete application!
If you liked this tutorial, and are planning to build this, let me know. I’d love to help you make it as complex as you’d like.
Write to me at vihar@appsmith.com.
I recently started investing and came across a product called Smallcase. The way it works is — experts create a diversified long-term portfolio of stocks & ETFs and manage it on a timely basis for you. I really love the idea of how stocks can be added into portfolios or baskets to reduce market volatility. Unfortunately, at the moment, this product is only available for Indian investors and that led me to create an app, where I could create a portfolio, and also create a custom index on top of it, with features to compare benchmarked indices like Dow Jones / S and P.
Building this kind of application from scratch would have taken me a lot of time; I would have had to choose a front-end framework, configure a database, and work on different visualizing frameworks to build time-series charts. With Appsmith, I was able to build this app in just a few hours. If you don’t already know, Appsmith is an open-source low code framework to build internal apps. In this blog, I will take you through the steps I followed to create the app.
First, let me share the specs of the app in a little more detail.
With this application, you can do the following:
In this blog, I will also dive into building some nifty time-series charts and build our stock index tracker that can compare with S&P 500, Dow Jones, and NASDAQ.
Here are a few screenshots of the application:
Now, let’s get started!
TLDR; I’ve used Appsmith, Fusion Charts on Appsmith, APIs from MarketStack, Alphavantage, and Google Sheets as the backend to build this application.
This application primarily uses Appsmith, an open-source low-code tool that can connect to any database, API, or GraphQL to build admin panels, dashboards, and internal tools. Appsmith also supports charting options; it has an in-built extension that uses Fusion Charts to create data visualizations; this made it much easier to build my own time-series charts. To pull all the stock data and prices in real-time, I’ve utilized free APIs from MarketStack and Alphavantage.
(Please remember to generate your own API keys if you’re following this tutorial to build a similar app! To know more about generating your own API keys, read this blog)
I’ve used Google Sheets as my backend to watchlist stocks and store customized stock portfolios and baskets.
The first step to creating portfolios, or as I like to call them, “baskets,” is to build a user interface. Through this, a form can take in our portfolio name, time created, and a logo for easy viewing… and some vanity! 😎
It took me less than 5 minutes to create this with Appsmith and Google Sheets; here’s how I did it:
Note: I’ve used the Cloud Version (Community Edition, which is free) of Appsmith; you can build this either on a local version using Docker or a self-hosted version of Appsmith.
Basket Name
Basket Image URL
Basket Create On
With this, our query is ready. Next, to build UI on Appsmith, you can just drag and drop widgets from the library on the right side of the screen. Appsmith’s canvas is quite responsive, and you can even drag widgets between two other widgets, and it will auto-resize, saving you valuable time! I added a container widget so that our app looks unified; we even have an option to add colors to this if we want to stylize the background a little more. I then dropped a text widget to set the app’s name and a button widget.
Here’s how it looks:
Neat, yeah?
Next, since we want there to be a form to create new baskets, we should get the button to open a modal. To do this, click the settings icon on the button widget to see the property pane.
Property pane is where we can configure all the properties of the widgets. You can open this, by simply clicking on the widget, and you’ll see it docked on the right sidebar, just as shown in the above screenshot.
We need to update the onClick property of the button and set it to open a new modal. You can create it there or drag and drop a modal widget onto the canvas. Both options work. You do you.
Next, we need three types of inputs for the form, so I added three input widgets to this modal. You can set the labels as follows:
Basket Name
Basket Image URL
Basket Create On
Here’s a Loom on how it looks like:
Things look in great shape so far, in order to be able to track the index of the portfolios based on created time, I thought it was best to use a pre-installed library on Appsmith since it’s not possible to track this manually. I used moment.js to do this.
We can set the Basket Created On default value to:
This will save time when the portfolio is created.
On Appmsith, we can write JS anywhere across the platform to add customization using the moustache {{ }} bindings. It also comes with the moment.js library; hence, calling the function will save time when these portfolios are created.
Lastly, I opened the buttons property-pane and set the onClick property to run a query and choose addBasket query.
With this, my UI is all set; lastly, I went back to addBasket query and set the Row Object to the following:
Note that we will be collecting the values from the Input widgets and passing them to the Google Sheets via the addBasket query.
Next, to display all our baskets on this page, we need to create a new API. I created another one called getBasket, from the Google Sheets datasource. I updated the query method to Fetch sheet row list everything from the excel sheet. Here’s a screenshot:
Next, we have to bind our queries to the UI widgets. This part can be done like this:
This is how it looks now:
Here’s what we’ve been able to do till now:
Now, we will work on adding stocks inside these portfolios. For this, it would be best to create a new page to search for stocks and add them to baskets.
Let’s create a new page; you can choose the option on the left sidebar and name it as ‘Basket Page’. The idea is to redirect to this page from Page1 and filter all the stocks present in the basket.
But how do we filter stocks? Usually, we do on a regular backed to consider an id and filter based on it. Similarly, on Appsmith, while navigating to Basket Page, I stored the value of the basket page to filter and display data on the Basket page.
I can use the code snippet I mentioned below on a new button widget placed on the list widget. So, when clicked, it should save the selected item on the list, redirect to the basket page, and filter accordingly.
We need to the button’s onClick property to:
Here, we need to use the storeValue from Appsmith to store the basket name in a variable named selectedBasket, the List1.selectedItem copies the data from the selected list item.
Next, we need to use the navigateTo function to redirect to a new page.
Before we add any stocks into our portfolios, we’ll have to ensure that this page filters my stocks according to the selected basked from page one. So let’s add a container and a text widget to display the Basket name.
Note that this value comes from the global store, so on the Text property from Text widget’s property pane, we will have to bind value from the Appsmith store, and this can be done with a simple line:
{{appsmith.store.selectedBasket}}
Alright, the next cool feature for us to add is a search function. This way, we can easily search for stocks and add them to baskets; for this, we need to add another button and modal with the following fields:
The table widget definitely deserves high praise. It allows us to add filters and sort results. We can add relevant stocks based on where they are listed on. For example, I could simply search NASDAQ, which filters stocks listed there. If you want to know everything that you can do with a table widget, you’ve got to check out this detailed blog.
Before I tell you how I built this, here is how it looks like:
The search feature works with a simple API from Stockdata, to integrate this, I followed the following steps:
https://api.stockdata.org/v1/entity/search?search={{stockcode.text}}&api_token=YOUR_API_HERE
To get this working, make sure you add API token from Stockcode here. Please note that I use moustache bindings here. This adds the values I’m searching for from the input widget dynamically. Now, let’s head back to the modal and update the names of the widgets.
I renamed the widget names to the following, to make it easy while pushing data onto sheets:
Input Widget: stockcode
Table Widget: stockSearchTable
Now, the search API takes the value from the input widget, and on the table widget, we can bind the results from the API for the following functionalities:
Next, we want to select which basket we want to add the searched stock to; for this, I just copied my API (getBaskets) from Page1, and bound it onto the selected widget with the following code:
Last, we need to save all this information onto a Google Sheet, so let’s create a new spreadsheet under the same Google Sheet and create a new API from the connected data source. I named this sheet Watchlisted Stocks and named the query addtoBasket.
These are the columns I have on my Google Sheet:
symbol
name
type
exchange
exchange_long
mic_code
country
watch_listed_on
basket
Now, on the query to collect all this information, we have to update the Row Object to the following:
With this last step, our watchlist will be ready. However, in order to show it on the page, we have to add a new table widget. Wait, I still had to pull all the watchlisted stocks from the google sheets. This is pretty straightforward, I create a new query from the GSheets datasource, set the method to Fetch Sheets Row, copy my GSheets URL, and update my Sheet Name to Watchlisted Stocks.
Now, we have to bind it on the new table widget, but here, it should only filter stocks that are added to this basket or portfolio, I do this by using a simple transforming when binding using the following code snippet:
As you can see, we’re now filtering our stocks based on the selectedBasket value from the Appsmith store that we saved while redirecting!
We now have all the portfolios and stocks ready.
Now it’s time for data visualization!
As mentioned, Appsmith’s chart widget comes with the Fusion Chart configuration, which makes it much easier to build time-series charts. The other thing I love about this is, I can even create candlestick charts for the stocks I watchlisted inside the application. These charts are used by traders to determine possible price movement based on past patterns.
First, let me show you how to fetch details of all the stock prices, using the MarketStack API:
http://api.marketstack.com/v1/eod?access_key=YOUR_API_KEY&symbols={{appsmith.store.current}}&date_from=2021-11-01&date_to=2021-12-12
Note: I’m filtering the data from 2020–11–01 to 2021–12–12, you can update this API accordingly based on your requirements.
In the API, as you can see, I have added an Appsmith store variable named current; this is to dynamically fetch the stock prices of the symbol or stock we wanted to analyze or add to our tracker.
Now, we need to write a code snippet under JS Objects, that stores all the data for all the stocks that are there inside my portfolio.
This is what I’ve used:
Here is what this code snippet does:
To create a time series chart, we need to drag and drop a new chart widget onto the canvas, below the table widget.
This is how it looks like:
It comes with a default configuration, so we will have to change the type to a Custom Chart to configure our data onto this. We will need to follow a particular format in order to do this. Here’s the basic config for Fusion Charts:
Here, we need to pass in three parameters, the chart configuration, data, and the categories that need to be displayed on the x-axis. Here’s the updated code:
Finally, this is how our graph will look like with the aforementioned configurations:
Additionally, I also created a list, that tells us the index value with simple math:
Imagine having your own custom app terminal to track all your stock indexes in one place. If you’re into crypto, you can extend this app to even have a crypto tracker.
I hope that you had success following this tutorial and building your own app. If you got stuck somewhere, I’d be happy to help you out :)
More content at plainenglish.io. Sign up for our free weekly newsletter. Get exclusive access to writing opportunities and advice in our community Discord.
Statistical data and database information is often represented using table models. These models might represent large amounts of data sets; hence there is a need for customization between table sets to help distinguish them. Finding a suitable application to help develop tables that meet these requirements is often an uphill task. Appsmith is an open-source framework that enables developers to build internal tools for applications and add functionality quickly. With Appsmith, we can also create tables, link them up to an API or database and perform CRUD operations.
In this blog, we will learn how to style tables in Appsmith. We will also learn how to customize different aspects of our table to change the appearance and how the table data is displayed. We will apply different styles to other tables to help distinguish them.
In situations where we are building numerous tables on Appsmith, we will need to add labels to each table to differentiate between them. Alternatively, we can also apply different styles to each table ranging from color gradients, cell colors, borders, and box shadows. Styling helps to improve the overall appearance of tables. When styles are used to identify specifically stored data, it makes it easier for viewers to pinpoint what they need to see in a table. For example, a table may have a specific cell color for table columns reflecting profit or loss in an account, making it easier to understand.
Appsmith tables provide an ordered form of representing data from a data source in rows and columns. This table can also be used to view large amounts of data, and the data can be arranged in the form of server-side pagination in which the amount of data displayed is limited per page.
Here are a few examples of some tables built with Appsmith:
Appsmith provides us with a property pane. The Appsmith property pane contains all the properties where users can connect to data and customize it with different properties. Numerous styles which can be applied to produce various results with the widgets can also be found in the property pane. Select the widget you wish to style and click on the cog-wheel icon at the top right to get to this style pane. The Style section is located at the bottom of the menu that pops up.
This panel may vary based on which widget is selected. The image above is the Style panel of the Table widget. Starting from the top, we have the following options:
- Cell Background,
- Text Color,
- Font Style,
- Text Align and
- Vertical Alignment.
We will go over these options in the course of this tutorial and discuss the effects of each of them.
In these style options, there is a JavaScript toggle button. Clicking on the JS toggle button changes the mode of input for the options and lets us enter strings of characters or JavaScript for the property we wish to apply. For instance, we can set visibility to none by toggling the JS toggle for the visible property and entering “false” in the field or entering {{false}}. The latter is Javascript enclosed in mustache syntax. We will talk more about what mustache syntax is and its usage later in this tutorial.
Below, I have a table widget with some data in it. If you select your table, you will get a popup with a gear icon you can use to edit your table.
Clicking on the gear icons opens up a property pane to edit the table. If you scroll down the menu, you will see a section to add styles to the table.
In this section, we will learn about the different styles provided by Appsmith and how they can be applied to produce different results with tables. The first two options in the Styles section allow us to change the color of our table’s background and our text color.
Above, I have selected a black color for my cell’s background, and I’ve also set my text color to white. Alternatively, you can use a different color other than the ones provided here by entering the Hex code for the color in the property field. An example is a purple color with the Hex code: #ed18cd. If you are looking for a site where you can pick colors from a palette and get the Hex code, you can check out Coolors or get the extension for your browser.
The next option gives us the ability to change the font size of the text in our table. There are different options to choose from, with “Heading 1” being the largest font size and “Paragraph 2” being the smallest font size.
Here, I have increased the font size for my table by setting my “Text size” property to Heading 1.
We can customize the font style and justify our text horizontally and vertically with the remaining three options.
Note that it is possible to add both “bold” and “italics” font styles simultaneously. The text-align property provides you with options to position your text either at the left, center, or right of your cell. In other words, it lets us set our text on the horizontal axis.
Vertical Alignment is used to make adjustments to the vertical position of our text in the table. The first option positions text at the top of their cell, the second positions the text at the center, and the last positions the text at the bottom of the cell.
Also, rather than applying these styles to the entire table, it is possible to target only a particular cell to apply these styles.
Appsmith has a feature to create styles for certain table elements that meet a particular criterion. We can define this criterion using JavaScript and state what styles should be applied. To do this, open the property pane on the column you wish to apply this condition.
Above, I have selected the phone column. We will add a condition to set the text color for this column. We will check if the value of each row in the phone column is even or odd and assign it a particular color. We can add JavaScript to the property pane elements using mustache. This is primarily JavaScript code enclosed with two curly-braces {{ }}. We can add JavaScript data or even functions to our table with this syntax.
{{currentRow.phone %2 == 0? "red" : "blue"}}
Some examples of writing JavaScript functions can be found in Appsmith Documentation.
The command mentioned earlier checks if the row is even; if it is, it will be red; otherwise, it will be blue. We can add this to the Text Color option in your column. Enable the JS toggle to write Javascript in the field and add the snippet above.
Here, the fields divisible by two in the phone columns have a text color of red, and the others have a text color of blue. This way, you can apply different styles to your table if specific criteria are met.
Appsmith allows us to add gradients as background color as we would normally add in a CSS Stylesheet.
Here is an example of a CSS gradient:
linear-gradient(90deg, hsla(217, 100%, 50%, 1) 0%, hsla(186, 100%, 69%, 1) 100%)
We can add this in our background property. The resulting color change will take place in the table widget.
I hope you found this article helpful and now have a better understanding of the Table Widget on Appsmith.
If you have any questions, please don’t hesitate to write to me at umavictor11@gmail.com. I will be happy to help you understand it better.
Uma is a software developer based in Nigeria who is familiar with various web technologies and frameworks. He is also keen on finding ways to explain things in simple ways. This article was written as part of the Appsmith Writers Program.
On average, a mid-sized company uses 75 apps to run its businesses! As teams grow and scale, internal apps, primarily administrative and departmental tools, help in sustaining growth. When manual processes get automated, it leaves more time for organizations to focus on their core growth-related work. Low code tools are an excellent way for businesses to solve their dilemma in allocating engineering resources. Low code platforms can help developers build custom internal applications at a fraction of the time traditional development takes. In this blog, we will build a web application using two low-code tools: Appsmith and Supabase.
Appsmith lets us drag-and-drop UI components into our application to develop the applications visually. It helps us connect the datasource to the UI components within a browser window. This speeds up the application building process. Supabase is a “Postgres database on the Cloud.” With Supabase, we only need to define table structure and SQL functions. Supabase takes care of generating REST APIs from the database schema.
As part of this tutorial, we will build an equipment management application. Creating such an application from scratch is laborious and time-consuming. We will use Appsmith and Supabase to rapidly iterate design and development and get feedback from our users early on. Both tools will significantly cut down development time, allowing us to deliver this solution in far less time.
Let us first understand the application and its uses in more detail.
Consider a video production company. This company has an inventory containing video cameras, lenses, and tripods. Employees borrow the equipment for photoshoots and then bring it back after the photo shoot is completed. The company needs to keep track of the equipment. They also need to make sure that people are accountable for the equipment they take. The company would need to know which employee has the equipment and when it will get returned at any given time.
Although we are using a video production company as an example in this blog, this scenario applies to other industries, for example, sports clubs that lend equipment to players and software companies that provide computers to their employees for remote work. An inventory system is needed for any organization where employees borrow the equipment to take it to a job site or work remotely.
We can implement this by using a simple spreadsheet or in paper form. But, spreadsheets or booklets are unmanageable once the equipment list or the number of employees grows. An equipment management system becomes a necessity.
In this blog, we will learn the following:
You can see the finished application here.
We will switch back and forth between Supabase and Appsmith to complete this project. Keep Supabase and Appsmith open on different browser tabs to follow this tutorial. We have a lot to cover, so let’s get started!
The first step is to use Supabase to create database tables. Here are the steps needed to create tables.
Create another table and name it the ‘employee’ table. This table contains three fields - id, name.
Add another table and name it the ‘checkout’ table. This table stores checkout transactions; it contains which employee checked out which equipment.
This table will have the following fields:
- id,
- created_at,
- equipment_id,
- employee_id,
- due_by,
- returned_on and notes. Fields’ equipment_id’ and ‘employee_id’ are foreign keys into table ‘equipment’ and ‘employee’, respectively.
We will be using this dataset.
Note: You can also use SQL from Supabase and write them as queries.
Follow these steps to read the employee table:
We can now build the Checkout form.
When the user clicks on the checkout button, we will open a modal containing a form. The form will allow users to select an employee and the date when equipment will be returned.
Here is how we can do it!
We want to set the default return date to a week from today’s date. We can calculate the default return date by adding 7 to today’s date. We can use external libraries such as moment.js inside our Appsmith application, which we will use in our application.
Replace default date with
{{moment().add(7, 'd')}}
You can read about using external libraries in the Appsmith application here. Now, we need to Select an Employee who will check out the Equipment. For selecting an employee - drag a ‘select' Widget.
Inside the options, we like to populate the list with employee names. We can derive the full name of an employee by concatenating last_name and first_name.
{{get_employee.data.map(
(emp)=>{return {'label':emp.name, "value": emp.id }})}}
When user checks out, duplicate the get_equipment API - and rename it to ‘post_checkout’.
{
"employee_id": {{SelectEmployee.selectedOptionValue}},
"equipment_id": {{TableEquipment.selectedRow.id}},
"due_by": {{DatePickerDueBy.selectedDate}}
}
This code essentially says: Construct a JSON with employee_id = Employee Id of the selected drop-down box, equipment_id = Current Row of Equipment Table, and Due_by = Value from the date picker.
We must provide a way to view a list of outstanding equipment checkouts. Let us create a new page.
First, let us build an API to read the checkout table. The process is similar to reading equipment or employee tables.
The only twist is that our checkout table is normalized. That means we have chosen to store ids for equipment and employees' tables instead of duplicating the record. In our UI, we don’t want to show ids.
For people familiar with REST APIs, that means multiple REST API calls to retrieve complete information. To avoid multiple REST API, we would need to use GraphQL. However, we don’t have to use GraphQL.There are simpler alternatives available.
Supabase’s REST API is based on PostgREST. PostgREST can detect foreign relationships and automatically returns embedded data. All we need to do is include the names of tables with fields. In our example, we like to retrieve all fields from the checkout table with corresponding records from employee and equipment tables.
Follow these steps to read the checkout data table:
/rest/v1/checkout?select=*,employee(*),equipment(*)
This will return values in JSON
[
{
"employee": {
"id": 1,
"first_name": "Smita",
"last_name": "Mehra",
},
"equipment": {
"id": 1,
"name": "Dell Laptop",
"image": "url..."
}
}
]
[See screenshot]
And you are done! We hope this was a great starting point for you to build the application. You can expand it further to include more features and make it as complex as you’d like.
If you’re feeling stuck, feel free to reach out to me! Email me at meera.bavadekar@gmail.com. This article was written as part of the Appsmith Writers Program. If you wish to participate, send an email to writersprogram@appsmith.com expressing your interest.
Meera Datey is a freelance web developer based in the San Francisco Bay Area. She specializes in helping small businesses design software solutions that deliver immediate value. This article was sent in as part of the Appsmith Writers Program.
Many companies use questionnaires to keep track of their employee’s health and general wellbeing. Because of the time and complexity involved in building one, many choose to go ahead with off-the-shelf solutions that may be quick to set up but have poor analytics tools. For example, the organization might be interested in knowing specifics about the use of the survey/questionnaires. For example (include one or two examples here) But there’s something better than off-the-shelf, and it can be built using Appsmith.
In this article, I will teach you how to build a custom employee survey dashboard to fit your specific requirements. We’ll achieve this by tying together the best open-source tools in the business to build powerful workflows.
We’re going to cover a lot, but specifically, you will learn how to:
You can peek ahead to see the app we’ll be building here. Let’s get started!
As mentioned earlier, we’ll be using Supabase as our storage DB. Signup for Supabase and create three tables; an employee, a question, and a responses table. You can seed the database with this dummy data
You should also go-ahead to set up N8N. You can signup for the cloud version or self-host it. Create a new workflow, and we’ll come back to it in a bit.
Lastly, signup for Appsmith and create a new app. Go to Datasources > Create New > PostgreSQL and fill the form to connect to your Supabase instance.
Awesome! With this, we have completed all the setup. Let’s begin writing queries.
We need to write a query to get questions from the DB. Let’s call this query get_questions, and it should look like this:
With the returned data, we can build a question filter. Drag in a select widget and configure its Options property shown below.
The name of the widget has been updated to q_filter
Similarly, go ahead to build a team filter. Name the select widget t_filter, and its Options property should be:
Using the filters we just built, we can write filtered queries i.e., to get employees based on the selected team and get responses based on the chosen question and team.
Create a new query for employees and update its name to get_employees. The query should look like this:
Similarly, the get_responses query for responses should look like this:
Using a table widget, you can display the employee completion status like so:
And, here’s the snipped used for the Table Data property:
In the last section, we wrote a query to get responses for the selected question and team. Now, we’re going to focus on displaying the data in charts.
From the widgets tab, drag a chart widget into the canvas. We want this chart to display the aggregate number for responses for a particular rating level, i.e. 26 employees rated 5. So for the Series Data property on the chart widget, use the snippet below:
And your chart should look like this:
We can also display responses by gender. For this, we’ll need a sex filter. You know the drill, so go and make one. Here’s mine (named f_sex):
And now, we can display the data using a chart widget set to a Pie Chart Chart Type. Here’s the snippet:
For some extra credit, use the principles above to build a filtered chart to display responses by age group. Here’s mine:
In this section, we’re going to look at how to send out emails from the dashboard using N8N.
For employees who haven’t completed a survey questionnaire, we need a way to resend it to them via email. Let’s build an N8N workflow for this.
The workflow would consist of two nodes, a webhook that accepts post requests and the second being a Gmail node. Here’s a snapshot of the workflow:
The Gmail node should be configured to send an email by setting the Resource to Message and the Operation to Send. The subject should contain a link to the questionnaire form, and the recipient email should be an expression that is evaluated the payload of the webhook as shown below:
Going back to the dashboard, we can create a new API to trigger this workflow. Go to Datasources > Create New > Create New API and enter the URL of the N8N webhook. Give the request a name i.e. send_email, set the request type to POST, and the body would be the email of the employee selected from the table:
Now, going back to the table widget, we can create a custom column of Column Type Button. Configure this column to run the send_email API when it is clicked. Thus, clicking on the button for a particular employee would resend the questionnaire to that employee via email.
Awesome! We’ve been able to build the employee survey dashboard. You can take a look at the app here https://app.appsmith.com/applications/61281a99695af65b46d75843/pages/61281a99695af65b46d75845
You can expand on this and add more features to the app. The floor is all yours! We’d love to see what you add next. By the way, give us a star any time you visit github.
In this article, we will be building a Shopify Dashboard that fits into your custom workflow. But before that, let’s set some context. Lots of store owners choose Shopify as their go-to online store. It’s a mature product with excellent features like the store admin panel and full API access.
That said, it’s not without its flaws.
Integrating with no-native Shopify services can be a real pain, and it’s almost impossible to build custom workflows with the Shopify admin panel. We’ve also published another post on how to make a Shopify admin panel.
In this article, I’ll be showing you how to overcome all of these hurdles so you can build a dashboard app for your Shopify store that fits into your workflow. We’re going to do this by covering the following concepts:
Feel free to peek into the app we’ll be building.
Sounds good? Let’s begin!
Lots of services provide secure access to resources via APIs. This makes it possible to design complex workflow and unlock new capabilities. Shopify is not exempt from this rule as we’ll be extensively making use of their APIs.
To get started, enable Private apps in your Shopify dashboard. Create a new app and configure the permission level. You’ll be presented with the following details to interact with the API securely: Your store endpoint i.e https://your_store_name.myshopify.com/admin/api/2021-10/ A username And also a password i.e shppa_cc*******
With these details, we can begin building the dashboard. So signup for Appsmith if you’re yet to do so, and create a new app.
In the new app, click on Datasource > Create New > Authenticated API. Be sure to set Authentication Type to Basic and then fill the form. Here’s a quick snapshot of mine:
Using the Shopify data source, let’s create a new API to get all products from the store. Call this get_products and it should be a request to the products.json route.
Now we have data coming into the app. Let’s go build some styled UI components to display this.
There are many widgets to choose from on Appsmith; the best part is that you can customize and style the look and feel of many. Let me show you how to do this.
From the widgets tab, drag a container widget into the canvas. In the opened configuration menu (called property pane), give it a Border Radius of 5 and set some Box Shadow. You should have a cool looking card container:
Now you can bring in a list widget into the container and bind the data from the get_products query like this:
And similarly, you can display the product image and name by accessing the data from {{currentItem}}. Here’s an example:
Cool! That’s how easy it is to style components by using the Styles section in the property pane.
So far, our app can read data and display it in the UI. Now let’s add a flow that allows us to write data. To do this, let’s build a product update feature.
Using the concepts illustrated in the previous sections, build an update form UI that looks like this:
And should be configured such that all input widgets are named and have default values based on the product selected from the product_list widget i.e the tile input widget is named up_title and has a Default Text of {{product_list.selectedItem.title}}:
Cool. Do the same for all the other input widgets in the form.
Now, using the Shopify data source configured earlier, create a new update query that takes input from the form widgets as parameters. Here’s an example:
You’ll also notice that the ID of the product to be updated is populated from the product selected on the product_list widget and used in the endpoint URL.
Awesome! To finish this up, go back to the form submit button and configure it to run the update query. We should also add a get_products query so that all data in the app is refreshed i.e:
And that’s how easy it is to pass dynamic parameters to API calls!
Lastly, let’s talk about how to integrate with Google Sheets.
This section will be quite advanced, so stick with me! We will build a bulk import functionality from Google sheet, a feature not natively supported by the Shopify API.
To get started, create a new page and under Datasource > Create New, click on Google Sheets. Authorize the datasource and create a new API that we’ll call get_products_from_sheets.
You can use this sample sheet as a reference for the Spreadsheet URL config. Here’s a sample configuration:
Now, you can build UI widgets to display the data returned as we did for the product list. In this sample, I used a table widget:
When the Sync button is clicked, we loop through the items and create each product by making a couple of API calls. Also, notice here that we have parameters passed to the API calls as the third arguments:
And here’s a snapshot of each of the queries call:
You can learn more about these resources/endpoints in the official Shopify docs.
Congratulations, you did it!
So far, we’ve implemented the core functionalities such as viewing, updating, and bulk import of products. But you can expand on this and add additional services i.e., payment with Stripe.
The floor is all yours! We’d love to see what you add next. By the way, give us a star any time you visit github.
Every application involves some level of CRUD operations, be it reading records from a database, creating or updating records, or deleting records. All of which is put together by well-designed application UI and logic.
In this article, I will show you how to build a task manager in Appsmith using Firestore as the database. By doing this, we will cover and solidify core concepts like connecting to databases, writing queries, infusing data to widgets, and writing custom functionality using JavaScript.
In this article, you will learn how to do the following:
Let’s get started with the first.
Before we go in-depth into using Firestore, you need to create an app. Signup for Appsmith cloud and click on the New button with orange. Now, we can connect the created app to the database.
Click on Datasources > Create New and then Firestore. Fill in the credentials to connect to your firebase instance. To make sure all details are correct, click on the Test button, after which you can save the data source.
To get your Service Account Credentials, go to your project settings in Firebase and generate a new Nodejs private key that will be copy-pasted into your Appsmith app.
Here’s a snapshot of my setup:
Using the Firestore data source, we need to query for data. Let’s write a query to get tasks from the database. To display some data, I have a simple collection called asana that has some seeded data. A query to get tasks would look like this:
The response data in the snapshot above shows the shape of each entry in the database. This will be useful in seeding your database.
Now that we have linked to Firestore and have some data coming in, let’s display that data in the app using widgets.
To display the data coming in, we’ll need a List widget. Switch to the widget tab in the sidebar and drag a List widget into the canvas. (The widgets tab is below the app name)
On the List widget, a simple binding can be written like this:
Similarly, we can display the data for each item in the List widget by bringing in Text widgets and writing their corresponding bindings.
That’s all you need to know about binding data to widgets; write {{}}, and you’re good to go.
Before we move on to deploying the app, let’s spend a few minutes building a form that will allow us to update/delete tasks.
To do this, drag in a Form widget into the canvas, and use a couple of text widgets to display the information about the task selected from the List widget, such as clicking on a new item on the list will automatically update the form. Your binding should look like this:
You should also do the same for the Datepicker, Input, and Select widgets required to build the form. For example, you should configure the selected widget this way:
![select widget configuration] (res.cloudinary.com/confidenceappsmith/image..)
You should also rename your widget to something more descriptive as I did in the Select widget shown above
Now, using the Firestore datasource configured earlier, you can write an update query like this.
And then, configure the submit button on the form to call the update_task query when clicked.
Wasn’t that was quite easy? Using the same principles, you can write a query to delete the task.
This is by far the easiest step. To deploy an app, click on the Deploy button to the top right corner of the screen.
You may also invite others to use/develop the app or even make it publicly available. You can use the share button just beside the Deploy button. This brings up a modal:
You’ve made it! You’ve learned the core concepts of building apps with Appsmith, and I’m sure you’re ready to put this knowledge to use.
I’m going to leave a link to the app here with more features added to make it production ready. Click on this text to see the app.
Awesome! Go into the world and build! (Also consider giving us a star on GitHub)
If you have specific questions for me, just send me an email and I’ll be happy to help!
Many internal tools, especially administrative applications, often require file uploading and file management features. File pickers, and file selectors, therefore, are some of the most used components in internal tool development. Developers experience numerous challenges when it comes to implementing these features resulting in delayed operations. This can easily be mitigated by using Appsmith to build and deploy applications quickly. Appsmith has a dedicated filepicker widget that can be used to upload files to any of the developers' preferred cloud storage services, such as Cloudinary, S3, among others.
In this short blog, we’re going to focus on one such widget, the filepicker. With this, you can upload files from your local machines to any cloud storage via API. You can upload files by implementing a POST API and reference the base64 or binary version in the post body.
1. The Allowed File Types properties allow us to restrict the types of files that a user (of our application) can upload.
2. The Maximum File Size attribute allows us to specify the total file size that a user can upload.
3. When the user selects files to be uploaded, we can immediately use an API or utilize the S3 plugin to upload the file's base64 to our cloud storage.
4. The visibility property controls the widget's visibility on the page. When the widget is switched off, the widget will not be displayed when the app is published.
5. There is a parameter that allows us to specify the maximum number of files that a user is allowed to upload.
In this section, we'll look at how the filepicker works. First, let’s set up a new application to get started!
Now, we’re all set to explore how the filepicker widget works in Appsmith.
Drag and drop the filepicker widget (as shown in the image below).
Now that we have our filepicker widget on the canvas, we can customize the properties as desired.
After selecting our file(s), we get the following result:
We'll go over each of the configurations accessible in the Appsmith filepicker one by one.
Label: This is used to set the label of the Filepicker from the default “Select Files” to any label of our choice.
Maximum No. of files: This allows us to specify the maximum number of files that a user is authorized to upload.
Maximum File Size: This property allows us to specify the maximum file size that a user can upload.
Data Type: This determines the data format of the files uploaded.
Allowed File Types: Allows us to restrict the types of files that a user can upload.
Accepts an array of wildcardsimage/*, exact mime types image/jpeg, or file extensions .jpg:['image/*', '.jpg', '.jpeg', '.png', '.gif']
Required: When turned on, it marks user input as a required field and disables form submission until the input is made.
Visible: Controls widget's visibility on the page. When turned off, the widget will not be visible when the app is published.
See the documentation to learn more.
Let's now explore how to upload single or multiple files using filepicker to cloud storage using the Cloudinary API.
We'll need to connect to our data source by clicking on the Plus icon next to the data sources link in the sidebar, then selecting "Create New" from the menu, as shown below:
After this, we should now choose the "Create New API" option. This will take us to the screen shown below:
We renamed the datasource from the default "Api1" to "Cloudinary API" in the image above to have a clear description.
We will be making use of the Cloudinary API: `https://api.cloudinary.com/v1_1/{cloud_name}/image/upload` where {cloud_name} is our cloudinary username.
The API requires our Cloudinary cloud_name and upload_preset.
To get our cloud_name and upload_preset, we follow the steps listed in the following sections.
The cloud name is obtained from our Cloudinary dashboard, as shown below.
An upload preset can be found in the “Upload” tab of our Cloudinary settings page, which we access by clicking on the gear icon in the top right corner of the dashboard page.
We then click on the Upload tab on the settings page:
We scroll down to the bottom of the page to the upload presets section, where we see our upload preset or the option to create one if we don't have any.
Adding the Cloudinary API URL and setting the header should look similar to what we have below:
Let's go to the "Body" tab and configure it, as shown below.
We specified the file(s) to be uploaded as well as our upload preset in the image above, and we configured our request body in a multipart structure.
Now that we've finished configuring the API, let's put it to the test before using it in our filepicker.
We will click on the FIlePicker Widget as shown below and select a file to be uploaded from our system.
Now let’s head over to the API section; the following is the test result:
Yay! That works! We’ve successfully tested our API and got a valid response.
Let's upload a single image directly from our filepicker to cloud storage by connecting to the API Datasource we just created. We will head over to the filepicker configuration and update the "onFilesSelected" property.
As seen below, we can add a success alert to show when the image is successfully uploaded and when there is an issue after selecting our query to be conducted.
The response below shows a success alert after uploading our image to cloud storage utilizing the Cloudinary API directly from our filepicker widget.
We hope that you found this short guide helpful. If you want to know how to upload or download files from S3, you can look at this document and follow this discussion. To learn more about how to upload a file to a local server, take a look at this discussion on our community forum.
Appsmith has more than 35 UI widgets, and these can cut your development time in half! To know more, head to our docs!
Did you get stuck somewhere? We’re happy to help! Join us on Discord today!
Olubisi Idris Ayinde is a software engineer, technical writer, and community builder. This article was written as part of the Appsmith Writers Program. If you’d like to write for Appsmith, send an email to writersprogram@appsmith.com expressing your interest.
Automation has become the ‘it’ thing in the world of business. The need for organizations to cut costs has forced them to improve internal processes to provide improved service while also conserving time. Unfortunately, it's not always easy for teams to streamline everything internally because they often seem like complicated processes - but there are ways around this. Using Appsmith, developing internal tools can cut costs, time and even improve your workflow by connecting services across specialized platforms with Zapier.
Zapier has thousands of apps and services that can meet almost all your business automation needs. Integrating Appsmith into the mix opens up a whole new dimension. In this way, you'll have a more efficient system in which you can connect anything from, say, a MailChimp email campaign to a Google form with data from your ERP or CRM systems delivered within the app!
In this blog, we will be looking at adding automation to Appsmith applications using Zapier.
Let’s get started!
Appsmith is a powerful platform to build admin panels, dashboards, crud apps, and internal tools. It allows us to create these applications with little to no coding required. We can build apps that integrate with just about any service you can think of. Today, Appsmith has more than 15+ data source integrations; a few popular ones include Postgres, MongoDB, Google Sheets. That's one of the best things about Appsmith -- it's completely customizable. But if you want to build apps with Appsmith, you will likely be doing some coding in JavaScript. Yes, we can use JS anywhere across the Appsmith applications to bind, transform and create actions to the data. In terms of UI, Appsmith provides more than 25 widgets with a wide range of styling options. While it's not hard to use Appsmith to build apps, you will need to start building them to get to the next level with Appsmith.
Now, let’s build a simple newsletter application that can help collect contacts from Appsmith and send Emails using Sendinblue via Zapier.
The idea of our newsletter is to collect emails from users and to maintain campaigns on Appsmith. Let’s get started by following the below steps:
Excellent, our UI is now ready; let’s create a new Zapier workflow to connect to SendInBlue and manage our newsletter.
Excellent, our UI is now ready; let’s create a new Zapier workflow that can connect to SendInBlue and manage our newsletter.
Webhooks are essentially a way to create a communication channel. It allows you to listen to an event and run a command or take any action you want. Here, the event will be triggered by an API call from Appsmith.
With this, whenever a new user subscribes to the Newsletter, he receives a confirmation Email and will be added to the contact list on Sendinblue.
And just like that, we could configure and build an entire Newsletter manager without writing code. This application can be extended in multiple ways, such as creating new email campaigns, filtering contacts, blocking users, and many more! The entire demo app of this tutorial can be found here. This is just one example of how you can automate your apps on Appsmith!
We hope that you will have a better idea of how to leverage automation in your Appsmith applications. For more information on automating your Appsmith applications, please contact me anytime at vihar@appsmith.com.
Every job has a set of critical and essential tasks that can feel mundane to execute. As a developer advocate, I love talking to developers and new users and helping them out on their journey with Appsmith. While I am busy doing this work, some tasks often slip into the basket of “I’ll get to it soon.” These tasks often include pushing out information about our new content in specific channels on Discord. This is crucial work and helps us, but it gets deprioritized when there are many other things to do. For social media, a tool like Hootsuite has been a game-changer for us. We also built our custom social media scheduler with Appsmith and automated it using n8n. We also wanted to solve this for our community on Discord. And that’s when we came up with our comprehensive push messaging system, which automatically pulls up content from various channels like our blogs, Twitter handle, and Luma events. We can just share it with users on our Discord server in just one click!
The Discord Message Pusher has been an excellent internal tool for us; the entire content and marketing team uses it, and guess what? No more pending tasks on our to-do lists! In this blog, I am going to discuss the steps involved in building this application on Appsmith. And hopefully, like me, you can make a customizable internal tool for your content team.
Let’s start!
In the first step, we will be creating a new application on Appsmith and integrating it with different data sources like Twitter, Youtube (YT), and Webflow. We’ll be using APIs to fetch all the information and render them on the Appsmith widgets. First, let’s set up a new application to get started!
Fantastic, the app is now set up, now let’s fetch all the information from a particular YT channel and render them onto a list widget.
In this step, we’ll be connecting to YouTube using APIs. Appsmith provides an easy-to-use IDE-based environment to connect to APIs and configure them. Now follow the below steps to fetch all the Youtube video links and their information.
We now have all the videos on Appsmith Youtube Channel (Appsmith YT ID: UCMYwzPG2txS8nR5ZbNY6T5g). Now, let’s use this query to render all the information on the application by following the below steps:
> The tabs widget allows us to create different navigation tabs. We’re using this as it’s more suitable for adding navigation between social platforms.
Listing all the Youtube Information to List Widget
We have our tabs ready. We’ll display all the videos from the Appsmith channel to the List Widget under the Youtube tab. Follow the below steps:
Image Widget Value : {{currentItem.snippet.thumbnails.high.url}}
Text Widget 1 Value: {{currentItem.snippet.title}}
Text Widget 2 Value: {{moment(currentItem.snippet.publishedAt).format("LL")}}
Text Widget 3 Value:
Here, we’re accessing the currentItem, which evaluates the element in the list values. On the first text widget, we’re displaying the Title of the Youtube Video; the second widget corresponds to the time it was published. On Appsmith, we can use moment to display the DateTime field in the necessary format. Cool right? Lastly, we display the YT video URL and add the id to the end of the URL.
Here's how the list widget looks like:
Excellent, next. Let’s learn how to push messages from Appsmith to Discord. Follow these steps:
Here, in the code snippet, we have a default message; this will help us push it directly to Discord. Also, we’re accessing the title and youtube video id from the list widget. Therefore whenever a new list item is clicked; the message automatically gets an update for you.
Let’s now use a Webhook to push these messages on a discord channel. For this, you’ll need a discord server and a dedicated channel.
Now follow these steps:
Awesome! When you choose or select a video from the list widget, the message automatically updates from the default value and will be pushed to the discord channel.
This part is almost similar to how we’ve listed all the videos from Youtube and drafted a custom message; the only thing that changes is the data source. Instead of YouTube, we’ll be using the Twitter API.
Now, let’s copy-paste all the widgets from the YouTube tab to the Twitter tab; for this, select the YouTube tab, hit CTRL/CMD + A, CTRL/CMD + C, open the Twitter tab, and hit CTRL/CMD + V. This will copy the list widget, the buttons, and the inputs.
Just like that, all our widgets will be copied to the tab. Now, let’s add the functionality to fetch all the tweets and push them to the Discord channel by following the below steps:
Following is the screenshot:
Now let’s update the widget properties.
To show all the tweets on a list widget, open the property pane and set the Items value to {{getTwitterData.data.data}}. Next, add two text widgets to the list widget and set the Text Value to the following:
Text Widget One: Tweet ID {{currentItem.id}}
Text Widget Two: {{currentItem.text}}
On the right, in the Discord Push Message Input placeholder to following:
This is how the application looks like now:
With this, we should be able to schedule/push our social posts from Appsmith to Discord. In case if you’re using other services like Webflow, you can utilize APIs to fetch objects from CMS and use the same template. Building this app from scratch, including writing snippets of code, is likely to take 30 minutes! Isn’t that fast?
If you liked this tutorial, and are planning to build this, let me know. I’d love to help you make it as complex as you’d like.
Write to me at vihar@appsmith.com.
Catalogue management is hard. But building a catalogue management app for your company is harder. Not only does the application have to connect to multiple tables/API, and pull data on inventory, price and even offers, but the application also needs a robust UI that lets the user manage this catalogue easily.
Not only does this take a lot of time to build and maintain, but direct access to the database or an API endpoint that could return private information could also prove to be a problem. GraphQL helps solve these problems inherently in the way it returns only what it is queried for.
Because of these benefits, GraphQL is a great interface to develop an internal application on and to make development and maintenance easier, a low-code tool like appsmith can be very useful and will help speed up the process of development.
In this tutorial, we'll learn to create an application to manage a games store's catalogue running a GraphQL backend. We'll be using appsmith to build the application and implement CRUD operations on the database. Here's the link to the final application.
Appsmith is an open-source framework that lets developers build dashboards, workflows, and CRUD apps with only the necessary code. You can connect to any API or databases like MongoDB, PostgreSQL, or MYSQL and get access to multiple widgets including charts, tables and forms for building a UI really fast.
To build this application, first, we’ve collected a dataset from Kaggle that has a list of games, their prices, rating, average playtime and genre they’ve belonged to. We’ve created a mock database out of this, hosted it on Hasura and exported them as GraphQL APIs. Below is an image showing some of the attributes of the dataset.
Here, as we can see, the response consists of data of games in a JSON format. Next, we’ll use Appsmith to utilise this database and build a Store Manager by writing different GraphQL queries.
To begin, we'll need to sign up for Appsmith (it's free!), if we don't already have an account. We can also deploy a Docker image on a server. For this tutorial, we're going to create an application on Appsmith cloud.
Below is a screenshot of the application:
To work with Appsmith, you need a database. This can be in the form of an API or a database. Appsmith supports MongoDB, MySQL, and PostgreSQL, among others. In this case, we’ll be connecting to Hasura, as it'll be our GraphQL backend server. To establish a new connection, follow these steps:
Here, we have the query stringified with moustache syntax to ignore all the line breaks. Inside the query, we have the table name we want to query steam_games with a limit parameter set to 100 and an ordey_by parameter to order all the games by the appid ascending order using the asc keyword. Inside the query, we’ll have to use the fields we want to fetch. Now hit Run to run the query. You should see a list of games in a JSON field in the response tab.
Awesome! You now have your store catalogue with all the games and their prices. Let’s now build a UI to display all these games on a beautiful table.
This will pull data from the FetchGames API we’ve set up in the previous section.
Beautiful! We now have our catalogue displayed on a table. Next, we’ll create a form where we can add new games to the database.
In this section, let’s look at how we can add new values to the database by building a simple UI. For this, let’s create a new Form on Appsmith that takes in all necessary fields to post in our game store database.
Name : nameInput
AppId : appIdInput
Average Play Time : avgPlayTimeInput
Genres : genresInput
Price : priceInput
You can simply do this by going to the input widget’s property pane and double-clicking on the existing widget name.
Below is a screenshot how the form should look like,
Perfect, we now have our UI ready; let’s create a GraphQl API to post data into the Database.
Here, we have an object consisting of a query key that holds the GraphQL query and a variables key with all the variables that need to be posted to the database.
Now, in the query, we have a mutation that lets us modify the server-side data. Inside the mutation, we’ll send the object that references the data we will be querying. The insert_steam_games_one allows us to post one object to the database. Inside this query, we can add the attributes we need to post. Next, we’ve associated the variables to the object from the created UI input widgets. The .text on the input widget name helps us get the text written inside the input.
One last thing now that you’re API is ready, we’ll have to call the API when we submit values from the Form. Now go back to the form, open the property pane of the submit button and set the onclick action to call an API. You’ll now find the list of APIs we’ve created, select the InsertGame API. Below is the GIF explaining the same.
Awesome, now that we have our POST request ready, we can try adding a new game to the store using the form we’ve created.
In this section, let’s look at how we can update the database’s values by building a simple Modal. For this, let’s create a new column consisting of a button in the table; once the button is clicked, we should see the modal with existing values and modify it after submitting it.
Name Input: nameEditInput
Default Text: {{Table1.selectedRow.name}}
Average Playtime Input : avgPlayTimeEditInput
Default Text: {{Table1.selectedRow.average_playtime}}
Genre Input : genresEditInput
Default Text: {{Table1.selectedRow.genres}}
Price Input: priceEditInput
Default Text: {{Table1.selectedRow.price}}
The default text will allow us to display the selected row data on the table.
Now, let’s create an API that performs update operations on the data.
Here, we have an object consisting of a query key that holds the GraphQL query and a variables key with all the variables that need to be posted to the database.
Now, in the query, we have a mutation that lets us modify the server-side data. Inside the mutation, we’ll send the object that references the data we will be querying. The steam_games_set_input allows us to update an object in the database. Next, we’ve associated the variables to the object from the created UI input widgets from the Edit Modal. The .text on the input widget name helps us get the text written inside the input.
Now we’ll have to call the EditGame API after the modal is submitted, hence open the button’s property pane and add the following code snippet under the onclick action:
This will update the item on the store and refresh the table, by re-running the FetchGames query.
This section looks at how we can delete the database’s values by building a simple button on the table. For this, let’s create a new column consisting of a button in the table; if clicked, the selected item should be deleted.
Open the Table Property Pane, and click on the Add New Column option. Now set the column type to Button and the label to Delete.
Now let’s write a Delete API and link it to the created button.
Now, in the query, we have a mutation that lets us modify the server-side data. The delete_steam_games allows us to delete an object in the database based on the selected appid. The appid from the table is referenced using this.params.appid.
Lastly, let’s call this API, after we click the delete button, go to the delete button property pane and select the Call an API action in the actions and select the DeleteGame API.
To refresh the table, after deleting an object, you can add custom JS in the button's onclick property:
This code snippet will first, delete the Game and then fetches the data again and updated it on the table.
You've seen how easy it is to build an application on Appsmith, specifically a catalogue dashboard. This guide covered how to create an application and connect it to a GraphQL, as well as how to create, read, update and delete data. You learned how to build interactive pages, work with widgets, and customize them for your purposes.
Building a dashboard with Appsmith is a fast way to build admin tools. Check it out if you’d like to save your developers time and get internal tools launched faster.
Cover Image: Photo by Charisse Kenion on Unsplash
by Kayode Alade
The daily standup has become a norm in the schedule of most developers around the world. A standup is a daily team meeting, at a specific time for a specific duration, that asks team members to answer three major questions:
The daily standup answers these questions but does not resolve them. When put to good use, daily standups increase team productivity and also enhance cohesion between all the parties involved.
In this tutorial, you’ll learn how to build a daily standup application using Appsmith, an open-source framework for building internal tools, admin panels, dashboards, and workflows. You’ll be using Appsmith to forward a summary of daily standups to Slack. Using a web framework like Appsmith is a much quicker way to add this feature to your workspace than building a completely new internal tool.
Appsmith comes out-of-the-box with prebuilt widgets like forms, charts, and maps that you can easily configure to your team’s needs. It also supports APIs and different types of databases. For more details about its capability, visit their official GitHub page.
First things first: head over to Appsmith to get a free account. After you sign up, it’s time to set up the user interface of your standup app.
Now that you’ve created your two pages, it’s time to start adding widgets. Your app’s first page will contain:
Let’s create the custom welcome message next:
Next, let’s display yesterday’s standup to-do on top so that you can see at a glance what you planned to do yesterday and then make plans based on that for today.
As mentioned earlier, the goal of a standup is to provide information about the previous day’s tasks, tasks that need to be done today, and anything standing in the way of accomplishing those tasks. Obviously, you’ll need a form to input all that information.
To create a form:
To finalize your first page’s UI, let’s add a table to display the users who’ve submitted their standup for the day:
Appsmith allows you to link data from several databases. For this tutorial, you’ll make use of Firestore.
Note that since you’re building an internal app, you can create more users and standups in their respective collections.
Mustache syntax ({{...}}) allows you to write JavaScript in Appsmith to read data from elements defined on a particular page. Let’s take advantage of this to pull information from queries or other widgets. First, let’s create the queries:
Note that widgets in Appsmith are global objects, so you can access their values simply by calling widget_name.value.
Continue to round out your app’s queries:
Note that queries can only be referenced on the page where they’re defined. If you need the same query on another page, you need to copy and rename it on the other page.
Now let’s connect these queries to the widgets in your Appsmith app.
To send the summary of your standup to Slack, integrate your Appsmith app with Slack using incoming webhooks.
“Incoming Webhooks are a simple way to post messages from apps into Slack. Creating an Incoming Webhook gives you a unique URL to which you send a JSON payload with the message text and some options. You can use all the usual formatting and layout blocks with Incoming Webhooks to make the messages stand out.” - Slack
Let’s dive in with the integration:
Let’s go back to your First Page in your app and configure the Submit button so that it sends a Slack message on submit.
Click the Settings gear for the Submit button. Below onClick, find the onSuccess field and from the Call An API option, select your Slack API.
At this point, your Appsmith app should look like this:
And as a result, your Slack channel should look like this:
You can check out this tutorial’s completed app on Appsmith.
In this tutorial, you learned how to build a daily standup app using Appsmith, including widgets that enable users to detail their accomplished tasks, their daily to-do lists, and any blockers keeping them from their goals. You then integrated your app with Slack, so you can send summarized standup reports to a specific Slack channel via incoming webhooks.
Have an idea for another app you’d like to build without reinventing the wheel? Check out Appsmith’s Getting Started documentation, or jump right in by signing up for a free account.
Author Bio: Kayode is a tech enthusiast specializing in embedded systems and system design and modelling. His programming languages of choice include C, C++, JavaScript, and Python. In his free time, he loves adding value to people's lives with technology.
Admin panels are an important part of every organization. They are necessary to serve customers better and run business processes smoothly. They help reduce management and people overhead significantly. But on the other hand, they take a lot of time to build and are troublesome and expensive to maintain. As a result, it is not the choice of project for most developers.
Thankfully, there are a lot of options available to developers today to build complex admin panels and dashboards fairly easily while making maintenance easier. An example of such a framework that we have explored, React-admin. We’ve written an article on how to use it. It’s better than building an admin panel from scratch, but it is still cumbersome to move from a simple admin panel to an admin panel that behaves like an internal app.
And that’s one of the reasons why we built Appsmith. Building Admin panels and internal apps should be easy and, more importantly, fun. Appsmith offers a drag and drop interface for creating UI elements and provides the option to write code wherever you may need to. You can build dashboards a hundred times faster on Appsmith, and that’s not an exaggeration.
For this article, I’d like you to imagine it's 2005. Netflix doesn’t stream video yet. You run a local DVD store, and you need software to manage your rentals. You’re the only developer in the organization. How do you go about building one that is fast, scalable and easily maintainable? In this article, I’m going to show you how to build an admin panel using Appsmith to manage DVD rentals for your store.
The app would have two pages. The first page would have a table listing all registered members of the store. The second page will have a table that holds all rental records. From here, new rental entries can be created, and existing rentals can be updated i.e from borrowed to returned. We would also be able to click on a customer from the first page and then taken them to the rentals page to see his rental history.
Before we begin, I’d like to give you a quick overview of the dataset we’ll be making use of. We’ll be using a modified version of the Sakila dataset. The database of choice is MongoDB on MongoDB Atlas and here’s the schema for each collection
That’s the overview of everything. Now let us get started!
Oh, snap! I almost forgot. Here are some of the core Appsmith concepts we’re going to cover:
We can get started now!
It’s quite important that our application is linked to a persisted data source because admin panels are almost always data-driven applications. This data can come from an API, a database, or a Google sheets table as we have the freedom to use any of these on Appsmith. We’ll be with the database route.
Create an Appsmith account if you do not have one yet and let’s begin to smith our application 😁
As highlighted earlier, our application would be based on a MongoDB database. Don’t despair if you would like to follow along and do not have a ready-to-go database. Here’s a database connection you can make use of. Mind you, it’s read-only (don’t forget to say thank you)
Username: article_reader
Password: 0HkfXpxVpvvSvUOx
Connection url: cloud.r4vra.mongodb.net
Database name: movie_store
Alright, we’ve removed all hurdles from the track, now let’s start racing!
Go ahead to create a new application from your Appsmith dashboard and give it a fancy name. Next, let’s connect to the mongo database. Click on the DB Queries button on the left panel on the page and select MongoDB from the list of supported databases. Now go in and supply the database credentials to the from, also give this data source a descriptive name i.e. movie_store or movie_store_db. I think I’ll go with movie_store. And lastly, hit the big green save button.
Awesome! We’ve connected the application to the database. We can now do some querying and build data-driven widgets. Let’s move on to the next section.
We now have a database connected to the application. The next thing we need to do is to create a widget that can be used to create, update and display data from the database. To achieve this, we need a way to fetch data from the database. This can be done on Appsmith by writing database queries.
Rolle up your sleeves because we’re going to be writing our first DB query! Click on the DB Queries section again, and you’ll see a button to create a new query on the MongoDB movie_store data source. Give the query a name i.e. get_customers, and select a read template from the list because we’re going to be reading documents from the Customer collection.
The get_customer query should find all customers in the Customer collection, sort them by email and return a fixed limit of customers. Your query should look like this.
Configure your query and hit the run button, and you’ll get a list of 10 customers. Sweet!
It would be much readable to display this data in a table. So let’s do exactly that. Click on the Add widget button just below the query editor, and you’ll get a new table widget on the canvas that has been automatically linked to the get_customers query. An alternative way would be to click on the Widgets section and drag a table widget to the canvas. Then, data from the query can be bound to the widget via the Table Data property on the widget’s configuration menu using moustache syntax.
It’s important you give the table a descriptive name. Consider changing the name from Table1 to customers_table
Go ahead to customize the table by re-ordering the columns and hiding columns you don’t like. We’ll also need to paginate the table, so on the table’s config menu, turn on Server Side Pagination and configure the onPageChange action (in the Actions subsection of the menu) to execute a DB query and then select the get_customers query.
We’ll need to update the query and add a skip property that calculates a skip based on the current table page number to simulate pagination. The moustache syntax would be very handy in this case to perform quick evaluations, so let’s make use of it. Your updated get_customer query should look like mine.
As you may have noticed, we are accessing the table’s page number from within the {{}} through the object bearing the widget’s name (customers_table in this case). You can learn more about writing Javascript in Appsmith here.
Click on the page number on the table widget now fetches new records. We’ve been able to query the database, bind data to a widget and perform customization on the widget. Good job!
Now, we’re going to create a new page to manage rentals. Click on the plus button on the Pages section of the left-hand panel and create a new page. Call this the Rentals page and update the name of the home page to Customers. On this new page, you’re going to be building a table to display rentals like we just did for the Customers page. You’ll need a query (should be named get_rentals) and a table widget (should be named rentals_table) for this. Your query to get rentals should look like this.
Where rentals_table is the name of your table widget on the Rentals page.
Good luck!
After completing the table on the Rentals page, the next feature we need to build in is the ability to create new rental records.
Here’s the game plan: We’re going to build a form that takes as input the status, rental data, film title, customer email, and return date. This form would be housed within a modal widget that would be triggered by clicking on a ‘Create new rental’ button. Now, you have a good overview, let’s get started!
On the Rentals page, head to the widget’s section and drag in a modal widget. In the modal’s config menu, update the name to create_rental_modal and set the Modal type to Form Modal. Now you see we have more space to work with.
With create_rental_modal open, drag in three dropdown widgets and two date picker widgets. The name of the first dropdown widget should be updated to customer_dropdown. Following this convention, go ahead and rename the other two dropdowns to film_dropdown and status_dropdown. For the two date pickers, their names should similarly be updated to rental_datepicker and return_datepicker. You should drag in a few text widgets to label these inputs.
We need a button on the UI to trigger the opening up of the modal. Let’s drag a button from the widgets section to the canvas. Give this button a new label i.e Create New Rental, and set the onClick action to Open Modal, then select create_rental_modal. Clicking on the button now opens up the modal.
Nice! We’ve completed the UI for the crate form. Now let’s wire it up with some queries.
The first query we’ll be writing for the create form would get all registered customers from the DB. We would use the returned data to build the options for the customer_dropdown. This query would be similar to the get_customers query from the Customers page.
Go ahead and create a new query named all_customers. It should be configured as shown below
Now, we can use the data returned from this query to build the options of the customer_dropdown. Open up the create_new_rental modal and head to the config menu of the customer_dropdown. Now replace the content of the Options section with the snippet shown below.
This returns an array of objects whose label and value are the email addresses of the customers from the all_customers query. You can play around with the dropdown and see that the options generated from the query. Sweet 🤩
Now you’re going to do the same thing for the film_dropdown. Create an all_films query and use the title field of each document to build the options for the dropdown. Your query should look like this.
Cool! For the status_dropdown, we can simply hard code the Options with this simple JSON array.
Don’t forget to set a default option for each dropdown widget The rental_datepicker and return_datepicker widgets do not require further configuration, and they are good to go. The last thing we need to do is to write a query that would create a new document on the ‘Rental’ collection using the data from the input widgets. Alright, go ahead and create a new query called create_rental and configure it this way.
Now we can go back to configure the big green Confirm button on the modal to run this query when it is clicked. We also want to close the modal and refresh the rental table when the button is clicked. Because what we want to do is a complex chain of actions, we can write some JavaScript to achieve this. Click on the JS button just beside the onClick button of the Confirm button and supply the bellow code snippet.
Great Job! Go ahead, give it a spin and create a few new rentals.
The flow for updating a rental is quite similar to that of creating a rental. We’ll need a modal that would be opened by clicking on a button. The modal would only contain form elements for updating the status and return date of the rental.
The only difference here is that we want the rental in question to be the one selected from the table. To do this, we need to head back to the config menu for the rentals_table and create a new column by clicking on the Add a new column button. Click on the gear icon of the newly created column and set the column name to Update. Also, set the Column type to button and set its Lebel property to Update. For its onClick action, it should be configured to open up the update_rental_modal which you’re going to build on your own.
And that all you need. Oh, you’ll also need to write a update_rental query too. It should look somewhat like this.
Now you have everything you need to know. Go ahead and build the update flow.
You’ve done a good job making it this far. I’m so proud of you that I’m going to leave the gif below. 🤗
We’ve been able to accomplish most of what we set out to do. We have a table on the Customers page to view all customers. On the Rentals page, we can view all rentals, create a new rental or update existing rentals. It was no small feat we accomplished.
I’ll like us to add one more feature. Let’s make it such that clicking on a customer on the customers_table takes us to the Rentals page, and then we can view all rentals made only by that customer.
We’ll need column buttons for each row like we did for the update flow. In this case, the onClick action of the custom column buttons would perform a navigation to the Rentals page and pass the selected customers’ email from the table as query params. Use the below snippet in the Query Params configuration for the navigation.
And lastly, we need to update the get_rentals query in the Rentals page to filter by customer_email coming in as a query param. We also add a fallback just in case no email is passed.
And that’s it! You’ve completed the app. 🥳️🎉🎉
It’s quite easy to hand off your application to the team that would make use of it i.e customer support. You don’t have to worry about an authentication/authorization flow; Appsmith does all the work for you.
There’s a SHARE button on the top right side of the page. You can easily use it to invite users to the application and set roles i.e app viewer or developer. No hassle is required!
Clicking on the ‘DEPLOY’ button to the right of the share button will publish all changes made in the editor to the hosted version of the application. Isn’t that cool?
We set out to build an admin panel, and we’ve seen how we can do it very easily using Appsmith. Going this route will drastically reduce the development time and resources put into maintaining the app.
If you found this tutorial helpful, please consider giving us a star on Github.
Cover Photo Credits: Photo by Serpstat from Pexels
Most founders talk to 10s, if not 100s of investors. Keeping track of the conversations, files shared, and specifics of each investor is hard. Most of the time, we find ourselves rummaging through our inbox for that last email received, the previous file sent or the following action steps.
Many founders rely on spreadsheets (Google Sheets, usually) to list down the bare minimum of next steps, notion or google docs for the notes, and everything else on email to “streamline” the fundraising process. We know that’s not efficient from our experience, and we thought why not take a leaf out of our sales team and use a CRM to track our investor conversations.
So we went ahead and built an investor CRM that we’ve been using for our fundraising. We used Appsmith and the Google Sheets Integration to build this. Feel free to develop or fork this application and extend it to however you want.
In this tutorial, we’ll build an essential Investor CRM, which will let you:
Here's a screenshot of how the app looks like:
Appsmith is an open-source framework that lets developers build dashboards, workflows, and CRUD apps with only the necessary code. You can connect to any API or databases like MongoDB, PostgreSQL, or MYSQL and get access to multiple widgets, including charts, tables and forms, for building a UI really fast.
Let’s dive right in!
To build this application, we’ll be using Appsmith’s Google Sheet Plugin. This will allow us to use our Google Sheet as a data source and help us build a custom CRM with a beautiful UI on Appsmith. Follow the below steps to integrate Google Sheets with Appsmith:
Awesome! Now that our Google Sheets Plugin is set up, let’s create a new Google Sheet and add the necessary fields required for Investor CRM.
Let’s divide our Google Sheet into two sheets; in the first Sheet named “Investor Details”, let’s add all the information regarding the inventors and their specifics. Following are the fields we’ll be considering:
In the second Sheet, “Notes”, let’s add all the notes/conversations related to these investors; we’ll use an identifier named id to filter our discussions based on the Investors. Additionally, we will also save the links to media/pitch decks that need to be shared with the Investors. Following are the columns we would need in the second Sheet.
To make this more precise, we’ve made a sample Google Sheet with some mock data here. We’ll be using the same Sheet throughout this tutorial, and you can either follow with this or create your own based on our requirements.
In the next section, let’s fetch all the investor information and display it on a beautiful table.
Now that we are connected to our Google Sheets data source, let’s connect to our Google Sheet and query all the data onto a table widget in Appsmith. To do this, navigate to the created data source under the APIs section and click on the New API button on the top right. Next, follow the below steps:
https://docs.google.com/spreadsheets/d/19ewbxuiNwfD5etHpb__jMzFYjVdYaeLSviC951htlsI/edit#gid=333192
Awesome, now that we have our data from the Google Sheet, let’s put this in a table; follow the below steps:
Perfect! We now binded our Investor Data into a table widget; you could play with it by opening the table’s property pane and displaying only required values or adding custom columns. Next, let’s add a feature to add new Investor Details to the Google Sheet from Appsmith.
In this section, let’s learn to add a new row from Appsmith UI to Google Sheet. With this, we should be able to add new investor details for our Investor CRM. Let’s start by adding a button and showing a modal that has a form to add all the details of the new investors. Follow the below steps:
Name the input widgets to follow to easily use them for other operations for our CRM.
Below is a screenshot of how our form should look like:
Now that we have our form ready, let's write the logic to push the values from the form to the Google Sheet whenever submitted. Follow the below steps:
Here, the key's are the column names in the Google Sheet, and the values associated with them are the names of the input widgets. The .text method is used to pick the text that's written in the input widgets.
Lastly, in the form below for the submit button, set the on click property to Call an API and call the addNewInvestor API from the options.
Our query is now complete, go ahead and try adding a new Investor Detail from the created UI. We should be able to see the updates on the Google Sheet automatically. Magical, isn't it? In this way, we could add new data using the Insert Sheet Row query. In the next section, let's see how we can edit existing row data from Appsmith.
Displaying on the table is cumbersome, hence let’s shrink our table and show all the details in a different container. Additionally, let’s give the functionality to edit the details when displaying them. With Appsmith, all these are pretty straightforward. Now, first, let’s reduce the width of the table and only show the Investor Name and Company, we can do this by opening the property pane and clicking on the eye icon to make the other fields invisible. Next, follow the below steps:
Drag and drop a container and add necessary input widgets to display the Investor Details. In this case, we’ll be adding the following:
Below is a screenshot of how our app should look like:
As we see in the image we have the Investor Table on the left, and the details on the right. Notice an Update Details button at the end? This button should help us the investor details wherever updated. Now in each of these inputs widgets, let’s use the selectedRow property from the table and display data.
Set the following to the Default text of input widgets in the investor details container:
Similarly, add the default text to the other widgets. Now, when a row is selected in the table you should have all the details of the selected investor in the investor detail container. Below is a screenshot of how it should look like:
Awesome! Our CRM is almost ready, but we missed one more thing in here; whenever we made changes in the input widgets and hit update details, the associated investor details should be updated in the Google Sheet. For this, let’s write a new update API that’ll help us update the values in the selected row of the Google Sheet. Follow the below steps:
Lastly, for the Update Details button, set the onclick property to Call an API and call the editInvestorDetail API. We should now be able to update the investor details by editing the necessary input widgets and clicking on the update button.
Awesome, now we have a fully functional app that allows us to manage all our investor contacts. Now let’s extend this application by adding a new page to save all the conversations, media files related to each investor.
A fully functioning CRM should also have all the details of conversations, files with the associated investor. For this, let’s create a new page where we display all the notes and conversations from the Investors. Follow the below steps:
Below is the screenshot showing the same.
Awesome, let’s add some details regarding the investor to the conversation page before we list down the conversations.
Next, drag and drop a table on the Canvas and in the table property pane under the Table Data, paste the following JS code snippet:
Here, we’re filtering the notes only based on the query parameter that’s passed in the URL. Remember, we set the id to 1. Hence, we should see the conversations only from the first investor.
Now on our conversation page, we’ve hardcoded the id parameter; that’s why we were able to see only notes from the first investor. Now let’s add a new column in the table that’ll redirect to the conversation page of the selected investor. We should pass the ID dynamically based on the rowIndex. Follow the below steps:
Awesome, this will send the id variable as the query parameter when navigated to the Conversation page, thereby filtering the notes based on the investor.
Now let’s add a new API that will add new conversations to the investor's details.
Awesome, this will add new notes to the Notes sheet in the Google Sheet. Also, make sure you call the addNote API when the “Add Notes” button is clicked.
Deploy your application on the cloud and share it with others, and that's it. We're done!
You've seen how easy it is to build an application on Appsmith, specifically a CRM with Google Sheets as a backend. This guide covered how to create an Investor CRM and connect it to a Google Sheets, as well as how to create, read, update and delete data. You learned how to build interactive pages, work with widgets, and customize them for your purposes.
We have made a slightly more robust application public here; try it out and let us know what you think. You can also check the live demo of our app here.
Cover Image Credits: Photo by Daria Nepriakhina on Unsplash
Businesses love loyalty programs. Loyalty programs are a proven and effective way to keep customers coming back to your business. The most simple loyalty program is offering discounts to your top quartile customers, so they keep coming back and get the best prices.
But if you're a small yet digitally savvy business, how do you set up and manage such a program to drive customer loyalty?
In this article, we will be building an admin dashboard to manage giving out discounts to loyal customers. Discounts will be assigned to customers based on their purchase history and will be available for use on their next purchase.
In this dashboard, we'll have a list of customers from where we can choose a customer we want to give a discount. On selecting a customer from the list, we can see all orders that have been made by that customer. We would also have a form that would allow us to give a percentage discount to the customer based on the total amount spent in the store by the user and set an expiration date for the discount.
You can check out the completed dashboard here 👈.
By the end of this article, you’d have learned how to build a Postgres admin panel using Appsmith. We’re going to cover core concepts such as
Now you’ve got a good overview of what we’re going to be building, so let’s get started!
As I mentioned earlier, we’re going to be building the discount management dashboard using Appsmith. Appsmith is an open-source platform that lets you create powerful apps/dashboards/tools quickly using a simple drag and drop interface.
Head over to appsmith.com and sign in. We’re going to be creating a new application, so click on the create new button. Please do well to give this app a creative name. The best I could come up with is Discount Dashboard.
The bread and butter of Appsmith is that we can connect to various sources of data by using APIs or talking directly to the database. We’re going to be connecting the application directly to our Postgres database, eliminating the need for a middle-man API.
To connect to the database, click on the + icon to the right of DB Queries then + New Datasource and select PostgreSQL. On the next page give the datasource a name and fill in the connection details.
A little side note here: This application was built using the mock Postgres DB connected to every application by default. Please feel free to use this if you do not have a database of your own
Since the application has been connected to the database, we can write queries to fetch data. The first query we’ll be writing would be to fetch users from the database.
Click on the + New Query button close to the datasource card to create a new query. Go ahead and give this query a name, let’s call it get_customers and it should be a select query:
Clicking on the Run button will fetch us a table containing all customers we have on our database. Now we build a list from which we can choose a customer using the data returned from this query.
We need to create a list of customers. Each item on the list will display relevant information about the customer such as the customers’ name, email, and picture. We’ll be using the brand new List widget to make this happen.
Head over to the widgets section, click on the + icon, and drag a list widget into the canvas. In the property pane of the list widget, rename the widget from List1 to customers_list. In the items section, delete the dummy data that was prefilled and bind in data from the get_customers query by referencing it using mustache template syntax shown below:
Now we’ve connected the data from the customers’ query into the List widget. All we need to do is to use that data. To do so, we can reference the currentItem object within other widgets in the list item and use its data to build up the list item. Here’s a gif illustrating how to do it.
Awesome! We now have a list showing all customers.
Continuing with the requirement for the application, we’ll want to see a list of orders for the customer clicked on from the list. To do this we’ll need to run an action whenever an item is clicked on the list.
Under the actions section of the List widgets’ property pane, let’s go and add an action for the onListItemClick event. From the dropdown list, select Execute a DB Query and click on + Create Query.
The new query we’ll be creating will be fetching all orders made by the customer. So call this query get_orders and set the query to:
Or we can write a slightly more complicated query that gets the product name for each order from the products table using the orderProductMap table:
Clicking on the run button will get the orders for the customer selected from the List widget. Now going back to the onListItemClick event, when the get_orders query is successful, we want to execute another database query to get discounts that have been given to the customer.
Go ahead and set up the query to get the customers’ discount. Your query should look like this:
At this point, we have a list of all customers, and clicking on a customer gets all orders made by that customer as well as the customers’ discount. It will be nice if we can neatly display the orders made by the customer.
We can neatly display the orders using a Table widget. Like we did with the List widget, go on and drag a Table widget into the canvas. You’ll also need to bind the data from the get_orders query into it and give it a nice name i.e orders_table. Your binding should look like this:
Also, you can hide some columns from the Table widget so that we only have the relevant ones showing.
We also need to display the discount amount and expiration time from the get_discount query. A couple of Text widgets will be sufficient for this. I’ll leave you to figure it out but here’s my solution:
Finishing up with the dashboards’ requirement, we’ll need a form that will allow us to give a percentage discount to a customer based on the total amount they’ve spent on the store. We will also be able to set an expiration date for this discount.
To build this form, we’ll need a few new widgets. We will be making use of a Dropdown, Input, and Datepicker widget. We’ll also need a Button widget to submit the form and a Text widget to label the Datepicker widget.
I have mine arranged as shown below.
Alright, let’s move on to configuring the form.
To configure the Dropdown widget, give it a new i.e discount_dd and supply the JSON array shown below as its Options:
The Input widget is where the magic happens. In this widget, we’ll need to sum all the amounts from the get_orders query and apply a discount based on the percentage selected in the Dropdown widget.
To do this we need to write multiline Js and this can be done with an IIFY(Immediately Invoked Function Expression). Set the Default Text of the input widget to:
Thus, the value of this widget will be the calculated discount. It’s a good idea to make the Input widget disabled to prevent manually updating its value. Give this widget a name i.e calc_discount. Also, the Datepicker widget should be named expire_dp.
All we have to do now is to write a query that will save the discount when the Button widget is clicked on. To do this create a new query called save_discount having the below body:
The above query will insert or update the discount of the selected customer.
Lastly, we’ll need to run this query when the Button widget is clicked on. We’ll also need to re-fetch the get_discount query and show a message on the UI to let the admin know that the discount has been successfully applied.
To do this enable JavaScript on the onClick action of the Button widget by clicking on the JS button close to it. Then set its content to the code below:
That’s it! We have a fully working discount management dashboard!
Sharing the dashboard we just built is an easy thing to do on Appsmith. You can easily hand off the application to the management team or invite developers to work with you by using the share feature.
Click on the SHARE button at the top right of the page and you’ll be presented with a dialog to invite users to the app and set their roles or permissions.
And lastly, you can publish all changes we made to the application by clicking on the DEPLOY button. Sweet!
That’s a wrap! If you found this article helpful, please do leave a Like ❤️. Feel free to share any concerns or questions you may have in the comments section. Also, we’d love you to check out our Github page here https://github.com/appsmithorg/appsmith.
Credits: Photo by Karolina Grabowska from Pexels
At Appsmith, we use Notion to manage our content calendar. We also work with a few external agencies and freelancers for some of our content. It is impossible to create granular access control and develop a workflow on Notion to run the process smoothly and thus, as soon as Notion released their API, we decided to build an application that helps us manage our entire content management in one place while giving our collaborators the necessary access only.
Our application uses our Notion (mock) Table as a data source and lets you plant, submit and edit articles on the application, while at the same time has a provision for integrating with an email service of your choice (we use SendGrid here) to send reminder emails or updates to people in the project.
In this tutorial, we’ll build an essential Content Management System, which will let you:
Check out the live demo here. Here's a screenshot of how the app looks like:
Appsmith is an open-source framework that lets developers build dashboards, workflows, and CRUD apps with only the necessary code. You can connect to any API or databases like MongoDB, PostgreSQL, or MYSQL and get access to multiple widgets, including charts, tables and forms, for building a UI fast.
Let’s dive right in!
Notion API lets us connect to Notion Pages and Databases. Now, let's look at how we can set up the API, gather all the required keys and connect to Appsmith.
In Notion, integration has a secret key; when added to a workspace, we could perform all the actions (create, read, update). We'll use the secret key of the integration to connect with third-party applications.
To work with the Notion API, firstly, let’s create a database for our content calendar.
You can also use this Notion page of ours, which can be used as a mock database. You can click on this link duplicate to one of your workspaces. Also, make sure to add the integration to this page to use the Notion API.
Now that we have our page and integration-ready, we’ll start building an App on Appsmith.
In this section, we’ll be querying data from Notion API. Follow the below steps:
Below is a screenshot of how the configuration looks like:
Awesome, we now have the response from the Notion API; let’s bind this onto a List Widget.
Now that we have an API containing data from the Notion Table let’s bind this onto a list widget to display all the details. Follow the below steps:
In Appsmith, you can access the API’s anywhere inside the moustache syntax using the API name.
Here, we’re using the query_data_from_database and mapping it to return item properties. This how the response looks like:
Awesome, now let’s add some widgets onto the list widget and show the details from the Notion API. Drag and drop six text widgets and set its Text property to the following:
Add six more text widgets next to them, where we’ll be binding their corresponding values from the Notion API.
Now in the text widget next to the Title text widget, set the Text property to the following:
Here the currentItem corresponds to a unique item in the list widget, and next, we access the Title property from the Items on our list and parse the JSON. Below is the screenshot of how the response looks like:
Great, we can now see our Titles from the Notion API on items of our list widget; similarly, let’s set the Text property of other text widgets to show the contents from the API:
The code for parsing through items changes based on the API response from the Notion API.
We’ve added some additional styles and added a button widget at the end so that admins can send Emails to the authors directly from Appsmith. Below is how the App looks like after we parse all the data from the Notion Table onto the Appsmith List widget:
We can also add a refresh button to the query_data_from_database query. For this, drag and drop the Button widget onto the canvas, set the Label property to Refresh. Next, open the onClick property, click the Call an API option, and select the query_data_from_database API. Now, whenever we click the refresh button, we should see all the new data updated on the Notion page.
For our content calendar, we can list all the details from the Notion Table. Now let’s add a feature to add new items on the table from Appsmith. Follow the below steps.
Following are the fields we’ve created for reference:
Now, let’s name these widgets (so that we can use them to refer in the POST API method) to the following:
Let’s create a new API that’ll add a new value to the Notion page when making submissions from the Appsmith form. Follow the below steps:
This is how Notion API allows us to add new items to a database. Here we'll also have to add the database id in the place of <db-id>. If we observe the body inside each property's content field, we added a moustache operation from which we'll take the input from the Appsmith input forms.
Now open the Submit button’s property pane, update the onClick property to Call an API, and choose add_an_item_to_database API. With this, we should add new data to the Notion table using the Appsmith form!
Our content manager now shows all the data and also has a feature to add new content ideas. Now let’s add an email integration to communicate with Authors via Appsmith. We’ll be using Sendgrid to achieve this.
Creating a Modal for sending emails:
Below is a screenshot of how the Modal should look like:
Configuring the SendGrid API:
https://api.sendgrid.com/v3/mail/send
This is the default configuration from SendGrid that lets us send Emails, but here we are dynamically passing the to-email, from-email, subject and content field from the widget’s we’ve created on the Modal. Now, set the onClick property of the form to Call an API and choose the send_email query. With this, we should be able to send Emails from Appsmith successfully!
Deploy your application on the cloud and share it with others, and that's it. We're done!
We've seen how easy it is to build an application on Appsmith, specifically a CMS with Notion as a backend. This guide covered how to create a CRM and connect it to a Notion API and how to create and read data. You learned how to build interactive pages, work with widgets, and customize them for your purposes.
We have made a slightly more robust application public here; try it out and let us know what you think. You can also check the live demo of our app here.
By: Veronica Stork
Tables are an important component of HTML that allows us to display data in rows and columns. There are several different ways to create tables.
If you don’t have many values to display, you can create your table using pure HTML. This is fairly straightforward but quite cumbersome if you have many values or if your data may change.
Alternatively, a table can be used to display information from a database programmatically or an API. Just fetch your data, then use JavaScript to append table rows for each datapoint retrieved.
If you need more interactivity, you can write JavaScript functions that implement more advanced features such as search and filter. This adds more functionality to your app but also more code and complexity.
When you build your table using these methods, you will also need to style and structure it in a readable way for the user. This is not difficult, but it can be tedious. Ultimately, the minutiae of correctly structuring and displaying your data will eat up time that could be better spent on the underlying logic of your app.
Appsmith is an open-source framework that lets developers build dashboards, workflows, and CRUD apps with only the necessary code. You can connect to any API or databases like MongoDB, PostgreSQL, or MYSQL and get access to multiple widgets, including charts, tables and forms, for building a UI fast.
Using Appsmith allows you to focus on the logic behind your tables instead of fiddling around creating the UI, connecting to the API, and reinventing the wheel in the form of filter and search functions. You can also see your table working in real-time as you build, a feature that is super handy when you’re trying to develop something quickly.
Your data should be an array of objects, with each object representing a row in the table. The object keys represent column names. You can populate your table with data in a few different ways: by typing the data directly into the property pane manually, by importing it from a data source using queries, or by connecting to an API.
To connect to an API, hover over the table data field of the property pane, and click on the lightning bolt icon. You will be presented with several options. Choose Use data from an API, then create new API. This will bring up a screen where you can paste the API URL in if you want to know more about creating a new API check out the docs.
Below is a screenshot showing the Table Data property and how we can connect to APIs:
Appsmith tables include features relevant to some of the most common use cases, including pagination, filters, downloading, searching, actions, and drilling into individual rows of data. You can use JavaScript to customise these features based on different use-cases.
Pagination is often required to display large amounts of data. If you have more data than rows in your table, you will need some way of splitting the data into separate pages. This can be accomplished using either offset-based or key-based pagination.
Offset pagination is based on the table’s page number and page size. For example, if you have a table with ten rows, your app will use ten and the current page number to determine which data to retrieve next. Let’s walk through how to set up offset pagination.
Enable server-side pagination in the property pane of your table. Make a query or API call that utilizes the pageSize and pageNo variables.
Run that query or API call from the table onPageChange.
Key-based pagination uses a value returned by the API to make the next page’s API call. If the API’s response includes URLs for the next and previous pages, you can enter those on the API settings.
Client-side filtering is included in Appsmith out of the box, but implementing server-side filtering requires a few steps. First, create a dropdown widget and fill it with filter values. Then call that API or Query onOptionChange from the dropdown.
In the above example, we are filtering based on the user status.
As with filtering, client-side searching is included in Appsmith out of the box. To implement server-side searching, you must call the API or query onSearchTextChange from the table and pass in the search box contents, represented by the searchText property.
Downloading also works with no additional setup: users can click the included download button on a table to download all of its data. You can also bind the download function to an action of your choice and set it to download whatever portion of the data you want.
In the above example, you choose the option to download the currently selected row’s data, but you can specify which portion of the data you want and give the file whatever name you want.
Actions in Appsmith represent ways in which your users can interact with the app and describe what you want to happen when they do. You can set the app to download data (as you saw above), call an API, open a modal, and more. All of the available options are listed when you modify action in the property pane.
Actions include the following:
A table is set to display Modal1 when onRowSelected is triggered in the example below.
Drilling into a single row of data is as simple as referencing the currently selected row using the selectedRow property. For example, {{Table1.selectedRow}} targets the currently selected row of our table. You can add a column name to narrow down the targeted data further. In the following example, {{Table1.selectedRow.name}} targets the name of the user represented by the currently selected row.
Making tables can be time-consuming and finicky, but with Appsmith’s rich table creation tool, you can focus on bigger structural and logical issues while letting it take care of all the nuts and bolts. Writing less code might seem strange at first, but you’ll quickly realize the benefits of working smarter, not harder.
I hope you enjoyed this introduction to Appsmith’s table features, which is just a taste of the whole suite of tools and features Appsmith can provide.
You can check some of the example app's that use the Table widget here. If you found this tutorial helpful, please consider giving us a star on Github.
Since its release back in 2012, Firebase has received lots of love from the developer community because it aims to remove the burdens many engineers have to deal with during development, including database, storage, authentication, hosting, and more.
One of its core products, the Firestore database, has been a game-changer in the database world because it allows highly flexible schemaless database access. But sometimes, it can be a bit challenging to work with, especially for new developers trying to build CRUD apps with Firestore.
Firestore and, by extension, Firestore is a great product, but it's only one side of the coin. However, to build production-grade applications, an interface is required for users to interact with and services provided by Firebase. Appsmith is the open-source UI framework that fills this gap if you're making something for your colleagues. Appsmith saves you the time of building UI and routers, focusing on the logic and the architecture of your app.
In this article, I will show you how to build CRUD applications using Firestore with Appsmith. We're going to cover the core concepts of Firestore, such as connecting to the database, reading data, and writing to the database by building a Todo app.
Here's what the finished application will look like:
Awesome! Let’s start hacking away.
Firstly, we need to create an app on Appsmith. Go ahead and sign in to your Appsmith account and click on the + create new app button. You should then be taken to a new app where we can begin building our Todo app. You might also want to rename the app from Untitled Application to something like Todo app.
Now that we have a new app setup, we can go on to connect to Firestore. Click on the + button to the right of the DB Queries section, and then the new data source button. We’ll be connecting to Firestore, so select Firestore from the list of supported databases.
On the opened form, fill in your Firebase connection credentials. Note that your Project Id can be gotten from your project settings in the Firebase console. Also your Database URL is <your_project_id>.firebaseio.com.
Lastly, you’ll need your Service Account Credentials. Go to the Service accounts tab in your project settings on Firebase. Click on the Generate new private key button. It’s going to download a JSON file, so copy its content and paste it in the Service Account Credentials input.
Save your connection and we’re good to go!
Now we have a connection to the database and we can begin to make use of it. Assume that we have a bunch of todos from the database with the following structure:
We can easily fetch todos from the database by writing a query. Click on the New Query button on the Firestore card, and let us write a query to get todos.
Give this query a nice name i.e _gettodos. Its Method will be set to Get Documents in Collection. For the collection path, fill in your collection path. And we can go ahead to set the Order By to ["-created"], doing this will sort the documents by their created date. Here’s my query:
Click on the Run button and you’ll get an array of todos from your Firestore database.
Now we can go back to the canvas and display this data using a List widget. Head to the widgets section and drag in a List widget into the canvas. On its configuration menu (called Property pane), replace the content of the Items field with the bellow binding that pulls in data from the get_todos query into the widget:
You wouldn’t notice any change but rest assured that we’re now feeding data from the query into the widget. Now we can go on to display the todos on the List widget.
You can delete the Image widget in the list as we do not have images in our todos
Drag in a few Text widgets to display the todos text and due dates. For each of the respective Text widgets, use the following bindings in their Text property to display data: For the task field
For the due date field. We’re using the built in moment library to format the due date
Great work! The app is coming to life!
Wouldn’t it be cool if we could create new todos? Yeah, let’s do that.
We’ll need a form for this. So, drag in a Modal widget into the canvas. You can close up the modal because will need a button on the UI to open it up. To do this, drag a Button widget into the canvas. On its property pane, set the onClick Action to showModal and the Modal Name to the modal we just created, that is Modal1.
Now clicking on the button should automatically open the modal. Sweet!
On the modal, we’ll need a few new widgets to capture the todo information. So go ahead and drag in an Input widget to collect the task info, and a Datepicker widget to collect the due date info. A screenshot of mine is shown below:
It is also important to rename the widgets so that we can easily access them later on. Here’s a gif showing how you can do that:
Awesome! Now we can go ahead to write the query to create a todo.
Like we did previously, go ahead and create a new query using the Firestore datasource we earlier configured. You can call your query _createtodo and set’s its Document Path to:
What we have above generates a random string ID for the document. Then set its Body to grab data from the Input widgets we configured on the modal:
Awesome! Now we can go back to write an onClick Action for the confirm button on the Modal widget. Enable the Javascript mode by click on the small JS button close to it and set it’s content to:
The script above will run the _createtodo query, after which it will update the list by running the _gettodos query and the close form modal.
Go ahead and give it a try. Fill in a task and set a due date, click on the button to see the magic happen!
The last feature we’ll like to add to our app is the ability to delete a to-do that has been completed. We’ll need a few new tricks to do this.
Let’s go-ahead to write a delete query. Call this _deletetodo. Set this query’s Method to Delete Document then it’s “Document Path* to the following binding which will read the todo_path from the local store API on appsmith:
Now, let’s go and drag a Button widget into the list. For the button’s onClick Action, we need to store the current todos path in the local store and then run the delete_todo query. We’ll also need to update the list by running the get_todos query. Here’s what you need:
Paste that in and give it a test run. Cool right?
We’ve been able to create a full blow CRUD todo Firebase app using Appsmith. Here a gif of the app in action:
Awesome! Now you can click on the DEPLOY button to deploy it and share the app with friends (be sure to update sharing permissions by clicking on the SHARE button).
If you found this helpful, show some love and leave a star on our GitHub repo https://github.com/appsmithorg/appsmith.
A content management system (CMS) is software used to manage the creation and editing of content, usually formatted articles containing images and videos. A very popular example of a CMS is the WordPress CMS. CMSs are very important tools for managing content because they make it easy to create, update, and delete data without any coding knowledge.
Appsmith is an open-source framework that helps developers build dashboards, workflows, pages, and CRUD apps very quickly. Appsmith allows you to build tools with little or no code, with the ability to connect to APIs or databases such as MongoDB, PostGreSQL, or MYSQL, as the case may be. You also get access to charts, widgets, and other customization tools for building a UI. Appsmith has more flexibility than off-the-shelf options, and it’s fast to build and easy to maintain.
In this article, you will learn how to set up Appsmith locally, create a new application, connect an API to it, and build a content management system using widgets and pages.
This section will focus on how to create a CMS as an Appsmith application, as well as how to set up and connect a SQL database for use in Appsmith.
For the purpose of this tutorial, you’re going to create a local instance of Appsmith using Docker. Read Appsmith’s documentation to set this up for your operating system.
After going through those steps, visit http://localhost/ in your browser to see the local version of Appsmith. Create a local account to log in. Next, click the Create New button to create a new application and name it CMS. This takes you to an empty workspace with a sidebar. On the sidebar, you should see items such as Pages, API, and DB Queries.
To work with Appsmith, you need a data source. This can be in the form of an API or a database. Appsmith supports MongoDB, MySQL, and PostgreSQL among others.
In this tutorial, you’ll connect to a local PostgreSQL database. To create the data models required for the CMS, go into the PostgreSQL command line, and create the database:
Connect to the database and create a DB table called Author:
Create a table, Article:
Create a table, Tag:
Create a table, Article_Tag:
By now, you should have a standard database with the tables Author, Article, Tag, and Article_Tag on it. Next, insert some data into the database tables by running the following queries, so you can view it when you build your user interface:
To connect to the appsmith_cms database from within Appsmith, go to the application sidebar. Click the plus icon near DB Queries, then click New Datasource, select PostgreSQL, and enter the connection details for your database.
Since you are on localhost, set the host address as host.docker.internal and the database name as appsmith_cms. Add your PostgreSQL username and password to the Authentication section and click Connect. Once connected, rename the new datasource as CMS.
In this section, you’ll create the first UI view of your CMS application. It will be a form with several fields, for title, content, cover image, and a URL. These form fields will take in all the necessary data for creating an article.
On the sidebar, under Pages, a new page called Page1 already exists. Rename it as create_article_page.
Before building the form, prepare the queries necessary for creating an article.
Click the plus icon near DB Queries and click the New Query button near the CMS Datasource to create a new query. Rename it fetch_authors from the default name Query1. This will be useful in displaying all the available authors in your database. Paste the following code in the query box and run it:
Create a new query called fetch_tags. This will be useful for displaying all available tags in your database. Paste the following code in the box and run it:
Create a new query called submit_article. This will be used to create a new article entry in the database.
Create a new query called create_article_tag. This will be used to create a new article_tag entry that associates a tag with an article.
Go to create_article_page > Widgets, and add a form to the page by clicking the plus icon. Drag and drop a Form widget to the page’s workspace. Click the settings gear to configure the form. Change the form name from form1 to create_article_form.
Next, let’s add a few fields along with labels.
To begin, add a Text widget and label it Title:, then drag the Input widget in front of it and change its name from input1 to title.
Below that, add a Text widget and label it Subtitle:, then drag the Input widget in front of it and change its name from input1 to subtitle.
Add a Text widget and label it Content:, then drag the Rich Text Editor widget in front of it and change its name from RichTextEditor1 to content. Delete the default text.
Add a Text widget and label it Cover Image:, then drag the Input widget in front of it and change its name from input1 to cover_image.
Add a Text widget and label it Author, then drag the Dropdown widget in front of it and change its name from Dropdown1 to author. In the options settings for this dropdown, add the following code:
Add a Text widget and label it Tags:, then drag the Dropdown widget in front of it and change its name from Dropdown1 to tags. In the options settings for this dropdown, add the following code:
Go to the onClick section of the Submit button’s settings, and select Execute a DB Query, choose the submit_article query, then in the onSuccess section, select Execute a DB Query > create_article_tag query. This creates an article entry in the database, and then creates the article_tag entry that links the tag and article together.
To test that it works, fill in the form with some test data and submit it. In the Article table in your database, you should see the new article row with data you just filled in.
Create a new page called all_articles_page. This page will be used to display all the articles available in the database.
Add a new query called fetch_articles and run it. This query will fetch all the articles in the database, as well the authors who wrote them.
On the all_articles_page, drag a table widget to the page and rename it articles_table. In the Table Data section of the table settings, set the value to {{fetch_articles.data}}. This will use data from the fetch_articles query defined above. By now, the table should be populated with a list of all the articles. The table automatically comes with search, pagination, and filter features.
Next, add a new column to the table and call it View. In the settings for View, set the Column Type as a button, label it View, and set the value for onClick as {{navigateTo('view_article_page', {"key": currentRow.article_id})}} after setting it to JS mode.
This means that when View is clicked, a user will go to the view_article_page.
Create a new page and name it view_article_page. Create a new query, get_article, and fill it as:
Go back to the view_article_page and add the following widgets and settings:
On the all_articles_page, add a new column to the table. Then add a button called Edit to the column. In the settings for Edit, set the onClick section to JS and add {{navigateTo('edit_article_page',{"key": currentRow.article_id})}} as its value.
Create a new page and name it edit_article_page. On this page, you’ll add a form to edit existing articles. You'll also make sure that the form is prefilled with the details of the article you want to edit.
Go to view_article_page > DB Queries > get_article and copy the get_article query to edit_article_page.
Go to the queries under the create_articles_page, click the three dots near fetch_authors, and select Copy to Page and then edit_article_page. Copy the query fetch_tags to the edit_article_page as well. Under the edit_article_page, you should see all the copied queries. Make sure that the getArticlesCopy ends with { appsmith.URL.queryParams.key }}; instead of {{ }};.
Create a new query edit_article_query and add:
Create a new query, new_article_tag_query, and add:
Create a new query, delete_old_article_tags, and add:
To build the edit_article_page page, add a Form widget to the page, click the settings gear, and rename the form edit_article_form. Change the form label to Edit an Article.
Add six text widgets to the form and label them Title, Subtitle, Content, Cover Image, Author, and Tag respectively, just like you did on the create_article_page.
Drag the Input widget in front of Title and Subtitle and change their names from input1 to title and subtitle respectively. Open the title widget and set default text as {{get_articleCopy.data[0].title}}. Also set default text for Subtitle as {{get_articleCopy.data[0].subtitle}}.
Drag the Rich Text Editor widget in front of the Content label and change its name from input1 to content. Set the widget's default text as {{get_articleCopy.data[0].content}}.
Drag the Input widget in front of the Cover Image label. Rename the widget cover_image. Set the default text as {{get_articleCopy.data[0].image}}.
Drag a dropdown widget in front of both the Author and Tag labels. For Author, change its name from Dropdown1 to author and set the default text as the following:
And the Default Option as {{get_articleCopy.data[0].author_id}}.
For the Tag field, change its name from Dropdown2 to tag and set the options as:
And the Default Option as {{get_articleCopy.data[0].tag_id}}.
In the Submit button's settings, go to the onClick section and click JS. Set the value as:
To test that the configuration works, go to the all_articles_page and click the Edit button on one of the rows. This should bring you to the edit_article_page, with the form prefilled with the selected row's data.
From here you can edit the article and then submit. Confirm that the article got edited successfully from the all_articles_page by looking up the row to see if the data changed.
Create a new page called authors_and_tags_page. On this page, you'll be able to view all the Authors and Tags. You'll also add the ability to remove and add tags.
Go to the create_article_page > DB Queries and copy fetch_authors and fetch_tag to authors_and_tags_page.
Create a new query, create_tag_query, and paste in the following:
Create a new query, delete_article_tag_query, and paste in the following:
Create another query, delete_tag, and add the following code:
To start building the page UI, add a text widget and name it Authors. Underneath, add a table widget and rename it author_table. Set the Table Data as {{fetch_authorsCopy.data}}. Reload the page.
Add a new column called Action. Go to Action's settings, set its column type as Button, and label the button as View. In the onClick section, set it as JS, and the value as {{showModal('view_author_modal')}}.
You just created a button on the table called View. When this button is clicked, you want it to open a modal called view_author_modal.
To create view_author_modal, drag a Modal widget to the page and rename it view_author_modal. Change the Modal Title text to View Author, set the Modal Type as a Form Modal, and delete the buttons in the modal. Dismiss the modal and click one of the View buttons on the Authors table. This should open up the modal.
Now add a Text widget and set the Text value to {{author_table.selectedRow.name}} in the settings.
Add an Image widget and give it an Image value of {{author_table.selectedRow.profile_picture}}.
Add a Text widget and label it LinkedIn:. In front of it, add another Text widget and give it a Text value of {{author_table.selectedRow.linkedin}}.
Add a Text widget and label it GitHub:. In front of it, add another Text widget and give it a Text value of {{author_table.selectedRow.github}}.
At this point, you should see all of the Author's information rendered on the modal.
Next, you need to create a table to display all the tags. Start by adding a Text widget and labeling it Tags. Underneath, add a Table widget and rename it tags_table. Set the Table Data as {{fetch_tagsCopy.data}} and reload the page.
Add a new column called Action. Go to Action's settings, set its column type as Button, and label it as remove. Set the button to Red as well. In the onClick section, enable JS and paste the value as {{delete_article_tag_query.run(() => delete_tag.run(), () => {})}}.
You can test deleting a tag by clicking one of the remove buttons on the Tags table.
Add a Button widget in the bottom right corner underneath the Tags table and label it Add Tag. Next, in the button's onClick settings, click JS and paste the value {{navigateTo('create_tag_page','SAME_WINDOW')}}. Here you’ve configured the Add Tag button to open a new page called create_tag_page.
Create a new page called create_tag_page. When the Add Tag button is clicked, it should go to this new page.
Go to DB Queries and create a new query called create_tag_query. Paste in the following:
Go back to the create_tag_page, and drag a Form widget into the workspace. Rename it create_tag_form. Then inside the form, add a Text widget and label it Add Tag.
Underneath, add a Text widget and label it Name:. In front of it add an input widget and rename it tag_name.
Go to the onClick section of the Submit button settings and select Execute a DB Query. Choose the create_tag_query. In the onSuccess section, select Navigate to, and for Page Name enter authors_and_tags_page. This means you want to navigate to the Tags page once a new tag has been created.
Test creating a new tag and checking that it is present on the Tags table.
You've seen how easy and fast it is to build a content management system on Appsmith. You’ve connected to a database and built pages and made them interactive. You’ve experimented with how Appsmith’s widgets work, and you’ve learned to customize them for your purposes.
If you’re looking for a fast way to create a CMS or some other internal tool with minimal need for developer hours, consider building it with Appsmith.
Like most companies, we use analytics and marketing automation software to run our daily operations and engage with different segments of users. We use Mixpanel, ActiveCampaign and Reply.io for analytics, managing lists and automation, and email engagement.
To determine which users we need to reach out to, we have a report we run on Mixpanel. Sometimes we need to send them a simple email, and sometimes we need to send them an engaging sequence of emails. This decision is again based on the report from Mixpanel. ActiveCampaign helps us with the one-off emails, but we use reply.io for engaging and personalised sequences.
This is what the process looks like:
We’re still young, and we look at most users we want to engage with personally, and doing this manually every day would take a lot of time and workforce. So we ended up building a dashboard on which, with a single click of a button, we can customise and send out emails to our users.
This is what our process looks like now:
It saves us a LOT of time and helps us keep our core focus on our users.
In this tutorial, we’ll be walking through different steps to build such workflows with various APIs and extend them based on our use cases using Appsmith.
Appsmith is an open-source framework that lets developers build dashboards, workflows, and CRUD apps with only the necessary code. You can connect to any API or databases like MongoDB, PostgreSQL, or MYSQL and get access to multiple widgets, including charts, tables and forms, for building a UI fast.
Mixpanel is a product analytics tool that’ll give reports based on defined queries. It also provides API, which we’ll consume on Appsmith to pull out all the reports of users who have invited others. Now, let’s follow the below steps to set Mixpanel API as a data source on Appsmith:
The API's and ids used in these tutorials are examples created for demo purposes. These do not depict the original data. Feel free to work with your APIs or follow along with these tutorials with the given examples.
Fantastic, we should now see the response from API having a set of users for whom we want to build customised email engagements.
In the next section, let’s show the users on a List widget and customise it based on our UI preferences.
Let’s use the List widget to show all the invited users from the get_users API endpoint. Follow the below steps:
Above, we have used the moustache syntax and consumed the get_users API, which was defined previously. In Appsmith, we can use the moustache syntax anywhere, anytime and write JS to manipulations. In this case, we are returning the important variables like email, last name, location of user, company to the list.
Following is a screenshot of how the evaluated value looks like after we add in the JS:
Now let’s drag and drop a few text widget’s on the first list item and bind the values from the list Items property.
For the first two widgets, set the values like Name and Email. Next, set the following text Values to {{currentItem.email}} and {{currentItem.first_name + ' ' + currentItem.last_name}} for the other two widgets. Now add one more text widget and customise it with a background colour such that it looks like a button; this is because whenever we click this, we can use the list’s selected item property and show the details of the selected user from the list.
Below is a screenshot of how our list widget looks now:
Now, let’s add a Map widget and bind the latitude and longitude to locate the user visually. Let’s follow the below steps:
Here, we’re setting the initial tag to the latitude, longitude and title from the list widget based on the selected item using the selectedItem property.
This is usually an array that takes details of markers we mark on the map. We need only one marker hence adding only a single object from the selected list item. With this, we should see our map, and when an item is selected, we can see the users' location. Simple right!
Below is a screenshot of the Map widget:
In this section, we’ll add one more workflow where when clicked on a button, we should be redirected to the list-item selected user’s smart look recordings. These smart look recordings are added in a different mix panel API which is protected. Hence we’ll be using an authorization mode to access this API. Follow the below steps to follow:
Authorization : Basic YmZkNDhhYjk1NzcxNTg4NjI0M2VhZDYyNzNhNDhlMTk6
content-type: application/x-www-form-urlencoded
Awesome, this is a custom configuration for our Mixpanel Report to fetch the Smartlook recordings, you can customise this based on your report or use this as an example. Now let’s add a button below the Map widget.
Now, whenever this button is clicked, we should be redirected to the Smartlook URL of that particular users. Hence, we have to use JS to solve this. Now drag and drop a button widget beneath the map widget and set the onClick property to the following:
Here, when the button is clicked, we navigate to a new page, and the target link is the link that’s returned from the get_recording. We’ve done some additional parsing to fetch the smartlookPlayUrl property.
If the API’s are slow, we can always increase the Timeout.
In this section, we'll be using the APIs of reply.io to send emails to the users shown on the list.
First, let’s make a simple UI, we’ll have a button labelled, send Email when clicked these email campaign should start.
For this, we'll be needing to create two APIs; follow the steps below:
1. Fetch the Emails from Appsmith API
In this step, we'll have to fetch the profiles from the Appsmith account. Hence, we need to consume one of our Appsmit APIs and pass in the Email that's selected on the list widget.
2. Send Email
Now, let's create one more API with reply.io to send customised Emails by clicking a button widget.
Now set the button onClick property to the following JS:
Here, we’re fetching the users and sending them the Emails using a reply.io campaign that's already created!
Deploy your application on the cloud and share it with others, and that's it. We're done!
You've seen how easy it is to build a customised workflow on Appsmith. Similarly, we can integrate the number of APIs and data sources and build customised dashboards.
If you like this tutorial, drop us a star on our GitHub repository here
Admin panels are at the heart of every business operation, be it sales, analytics, user management, and so much more. That said, it isn't easy to find the right tools to help you build robust and scalable systems without spending too much time.
Django admin has been the go-to solution for many developers over the years. It provides a fast, easy-to-use, and highly maintainable framework for building full-stack applications and admin dashboards. These reasons make it a great choice to build admin panels.
To show you how to build admin panels with Django, we will build a dashboard for moderators to manage business reviews. All of this will be built on Postgres and the Public Yelp dataset.
Here’s a sneak peek of what we’ll be building:
Awesome right? Let’s get started!
We start by setting up a project. A project is a collection of settings for an instance of Django, which includes a database and app configuration. A project may contain multiple apps, but we are only going to need just one.
To set up a project for our Yelp review dashboard, use your terminal and cd into a directory where you’d like to store the project and run the below command:
When that’s done, cd into the yelp directory that was created and start up the server by running the command below:
The server automatically watches the project for changes, so you don’t need to restart it manually
In Django, you can have multiple apps inside a project. This means that apps are modular and can be used in multiple projects.
Go ahead and create a reviews app that will hold the code for the dashboard by running the below command:
You’ll notice that a reviews directory has been created with a couple of files. This is where all the code will go.
Next, we’ll need to let Django know about the reviews app we just created. We do this by registering the app.
To register the app, open yelp/settings.py file and add reviews.apps.ReviewsConfig to the INSTALLED_APPS list. After adding this, INSTALLED_APPS should look like this:
When that’s done, move on to configure your database connection in the DATABASES dictionary:
Save the changes and run the below command so that Django can set up tables in the database for the app in the INSTALLED_APPS list:
The last thing that needs to be done here is to modify the path of the admin dashboard in the yelp/urls.py file so that it is mounted on the root path instead of /admin. Update the urlpatterns list to:
With everything set up, we can continue with creating modes that describe the database layout. Models also show relationships between tables and can be used to specify validation and the widgets that Django will create for the dashboard UI.
We are going to need three models: one for businesses, users, and reviews. To create these, head to reviews/models.py and paste the below code:
You’ll notice that each class represents a model of a table in the database. Each model has variables that represent the fields. The fields are annotated with their respective field types and validation/relationship where necessary.
Now let’s create migrations for these models. Run the below command to do this:
Then apply the migrations
Taking a look at the database, you’ll notice that tables for reviews_business, reviews_user, and reviews_review have been created. At this point, you can import the yelp dataset.
Download the public Yelp dataset and import it into the reviews_business, reviews_user, and reviews_review tables respectively.
Are we ready to take the app for a spin? Not so fast. You’ll need to create an admin user to be able to view the site.
To create an admin user, run the following command and answer the prompt:
Once that’s done, start the server(if you previously closed it) and visit http://127.0.0.1:8000/:
After logging in, you’ll notice that none of the models we created is showing up. Let’s fix this in the next section.
To make the models from the reviews app visible in the admin panel, you’ll need to register them in the reviews/admin.py file.
This is quite easy to do. Add the below code to your reviews/admin.py file:
Save the file and head back to the browser. Upon reloading, you should now see Business under the Review app.
Easy as pie, right?
Play around with the dashboard to see the power of Django. But you’ll notice that the way data is displayed a little off, and we can’t see reviews for each business. Django gives us the room to improve user experience, so let’s do that.
We can make the reviews dashboard much better by adding some options to customize it.
Head to the reviews/admin.py and replace its content with the below code:
Save the file and head to your browser. You’ll immediately notice that you have a much better dashboard experience.
We can further make the dashboard cleaner by removing the annoying AUTHENTICATION AND AUTHORIZATION app that shows up by default.
To do this, add these lines to your reviews/admin.py file:
Save the file and reload your browser. Now we have a super clean functional Django reviews dashboard.
Now that the application is fully built, you can play around with it. This dashboard makes it easy for moderators to search for a business and approve reviews made by users.
Here’s everything in action:
And that’s a wrap!
If you found this article helpful, please leave a like and check out our awesome product for building internal tools appsmith.com
Managing leaves is hard. But sudden issues can arise with anyone, anytime, and organisations must keep a clear record of all the employees leaves to maintain proper working with constant efficiency month-by-month. But there's no time to really set a system in place for accountability, and they were forced to use Google Sheets to maintain these.
But not everyone are comfortable using Google Sheets, anyone can make edit’s to it once given access, and the process of approving and rejecting leaves by founders or managers is out of context. Hence, we at Appsmith came up with an internal app for leave management. It’s minimal and super easy to use.
Here’s a quick sneak peek of what the app looks like. This is forkable, customisable and can be shared across organisations and teams. This tutorial will walk you through building this application with Appsmith and its Google Sheet Integration.
Appsmith is an open-source framework that lets developers build dashboards, workflows, and CRUD apps with only the necessary code. You can connect to any API or databases like MongoDB, PostgreSQL, or MYSQL and get access to multiple widgets, including charts, tables and forms, for building a UI fast.
Following are the table of contents:
Let's dive in!
In this tutorial, we’ll be using the community edition of Appsmith Cloud to build the application. However, if you want to build this on a local instance and deploy it on your server, you could set up Appsmith’s on-prem version by following through with this documentation here.
Now let’s follow the below steps to setup Appsmith Cloud and GSheets:
The Google Sheets integration on Appsmith helps us use Google Sheets as a backend or data source and perform multiple operations without writing any piece of code.
Awesome, we now have access to all your google sheets from your Google account. Now let’s create a new Google Sheet and add the necessary fields to build our leave management dashboard.
Here’s a mock Google Sheet that we used to build the application. Feel free to copy the same google sheet to your account and try it out, or you could create a new one instead.
Following are the Sheets and fields that we used to build the application:
Sheet One: Users
This Sheet has all the information about the company’s employees and their roles. Following are the fields:
NameEmailAvailable LeavesLeaves AppliedTotal Leaves
Sheet Two: Leave Requests
This Sheet has information about leave requests requested by the employees and their status if they are approved. Following are the fields:
NameStart DateEnd DateTotal DaysReasonOther ContactStatus
We’ll connect to this particular Google Sheet and build a UI to create and list our leave requests in the next section.
Firstly, let’s build a Google Sheet API using the GSheet integration Appsmith. To do this, click on the Leave Management Data Source you’ve created in the previous section and hit NEW API. We should see the following screenshot:
Follow the below steps to list down all our leave requests:
3.Lastly, hit the Run button on the top right. We should see the data that's inside the Leave Requests sheet. Now let's create a new table and display the data.
4. Click the + icon next to Widget's, drag and drop a new Table widget onto the canvas. We can configure the Table Widget by opening its property pane by clicking on the cog icon on the top right of the table widget.
5.Now, copy-paste the following JS code snippet into the Table Data property inside the table's property pane:
Awesome! Here, we call the getLeavesRequested API and use the filter method to filter the object's based on the user_name and the leave status. In my case, the name inside the GSheet is Iron Man, and I'm matching the same with my username on Appsmith. We can do that by using Appsmit's internal store. Here, appsmith.user.name returns the user name Iron Man in my case. Similarly, say your profile name is Bat Man. Then, you should filter all the leaves that are named after Bat Man in the Google Sheet.
Now let's add an option to create a new leave request and post it to the GSheets. Follow the below steps:
Now drag and drop the following Widget's on the modal to create a form:
{{moment(DatePicker2.selectedDate).diff(DatePicker1.selectedDate, "days") +1}}
Our form is now ready; let's create a new API from the Gsheets data source that lets us post values from this form to the Leave Requests Sheet:
Follow the below steps to list down all our leave requests:
4.Add the following snippet in the Row Object property:
As you can see, we're setting the Status of requested leave as REQUESTED. We'll be changing this to APPROVED or REJECTED based on the actions from the leave manager admin page in the following sections.
Fantastic, now, when we add details on the form and submit it, we should see a new entry on the Gsheet. But we have one problem here, and the leaves on the table are not updated. So, for this, let's create a workflow that submits the data and refreshes the table data when the leave is requested.
Now open the modal and set the onClick property of the submit button to the following:
Here, we create a workflow that does the following:
We'll also create a new API from the Sheets data source getUserDetails that fetches the names in the Users sheet. For this, just copy the getLeavesRequested API to the same page and change the Sheet Name to Users. This will get all the User's that are there in our org.
In the previous section, we created a table and form to create and display all the leave requests. Now let’s build an admin dashboard where we could look at all the leaves requested by the team and accept or reject them. Let’s follow the below steps:
With this, we should be filtering all the row’s from the Leave Requests sheet that has leave status set to REQUESTED. Now let’s add two buttons that will allow us to update the status to Approved or rejected. Follow the below steps:
Similarly, create one more API named rejectLeaveStatus and set the Row Object as following to reject the leave:
Let’s set the Approve to button onClick property to call the approveLeaveStatus API and the reject button to call the approveLeaveStatus. Additionally, onSubmit, you can call the getLeavesRequested API to refresh the Table data. Below is the GIF showing the same:
This section will notify the user if the leave he applied for is accepted or rejected. For this, we’ll be using the List Widget and display all the leaves that are approved and rejected. Follow the below steps:
Next, drag and drop a few text widget’s and bind the list widget data using the currentItem property.
Finally, this is how the List widget should look like:
Finally, we've added some container's and added some additional information to make the app UI more beautiful. This is how the final look's like:
Deploy your application on the cloud and share it with others, and that's it. We're done!
You've seen how easy it is to build CRUD Apps and Workflows on Appsmith. Similarly, we can integrate the number of APIs and data sources and build customised dashboards.
If you like this tutorial, drop us a star on our GitHub repository here.
For a content management team in any organization, things can get chaotic between ideating, strategizing, content creation, and distribution. Looking after multiple social media platforms can be overwhelming; this is where social media schedulers come in handy. However, for an early-stage organization, subscribing to these tools can be an expensive affair, and they do not solve the organization’s specific requirements. For example, at Appsmith, we focus our distribution through Twitter, Discord, Slack, and Linkedin, and we wanted a customizable solution more suited to our needs. Our cross-platform scheduler can send a message across four channels with just one click, and we made this using Appsmith and automated the workflow with n8n.
And building this is not that difficult!
This blog will take you through the different steps involved in building a workflow like this. You can extend this and customize it further to address specific requirements.
In this tutorial, we’ll be using the local environment of Appsmith to build the application. However, we can always export and then import Appsmith apps to different environments (cloud, self-hosted, local).
The recommended way to use Appsmith locally is to use Docker; for detailed instructions, follow the documentation here.
Next, create a new account or sign in with an existing account and redirect it to our dashboard. Now, let’s create a new application and build a minimalistic UI for our social broadcaster by following the steps listed below:
Awesome! We will build a simple UI with Appsmith widgets to broadcast messages onto different social platforms in the next section.
Appsmith has a great set of widget (UI Components) collections for us to build internal applications. We'll be using a few of these widgets to create a form that enables us to write messages and select options to broadcast to social platforms of choice.
We now have the basic UI for our broadcaster. Now, let’s create an n8n workflow and integrate it with Appsmith!
In this tutorial, we will be setting up n8n in our local environment using npm (node package manager). Here’s the command to install n8n globally on your machine:
n8n helps you create powerful workflows by syncing data across 200+ apps. No coding is required.
Post-installation, type in n8n on your terminal or command prompt; it will open n8n editor on [http://localhost:5678/](http://localhost:5678/). Here we can create workflows and save them on local env. However, you can always import-export n8n apps in different environments.
Here’s a screenshot of the n8n editor:
Now, let’s create a workflow that’ll broadcast messages onto different social platforms. Follow these steps:
Following is a screenshot of how the workflow looks like:
We now have a clear picture of how our workflow looks like; let’s pass the data into n8n from Appsmith using the webhook.
Appsmith and n8n will be communicating through a webhook.
A webhook (also called a web callback or HTTP push API) is a way for an app to provide other applications with real-time information. A webhook delivers data to other applications as it happens, meaning you get data immediately.
Follow the below steps to configure this:
Update the TEST URL from your n8n environment.
Here, we’re sending all the required information from Appsmith to n8n using webhook through the request body.
The {{ }} moustache operator in Appsmith helps write JS anywhere and access widget properties.
If the nodes are throwing any errors, you can click on the pause icon on top of them to ignore them from execution.
Awesome, this should send the data to the webhook. Let’s add validations to the workflow with the data sent from Appsmith.
Appsmith <> n8n Workflow Configurations
Now, add the necessary API keys to the social nodes. If you’re using the n8n.cloud account, you can directly authorize each application by logging into your social media account.
After authorization, we’ll need to configure the if-nodes; here, we’ll add the expression from the Webhook, and based on the condition, we’ll be accessing the social nodes. For this, let’s use the contains operation on every node.
The value1 is set to {{$node["Webhook"].json["body"]["medium"]}}
The value2 is set to discord, linkedin, twitter, slack based on the condition from the node.
Lastly, we’ll need to execute the workflow and use Appsmith UI to cross-post content across selected social apps.
In this tutorial, we learnt how to automate content across social media by using Appsmith and n8n. In short, we used Appsmith to build UI and n8n to create automated workflows. With this combination, you could make scores of other similar internal applications that can connect to multiple services and data sources. For example, you could quickly build a CRM that can integrate with numerous email services, or you could automate code reviews and CI/CD pipelines.
We hope you found this tutorial helpful! Let us know if you made an app using Appsmith, and we would love to feature you.
Join the community! Come chat with us on Discord, or jump in on Github directly!
Appsmith is a low-code open-source framework that’ll help build your internal applications, admin panels, CRUD apps, and many more 10x faster. In this tutorial, we’ll learn how to deploy Appsmith on DigitalOcean by using the Appsmith droplet from Digital Ocean’s 1-Click Apps Marketplace and host it on your custom domain.
To get started, you’ll need an account on DigitalOcean; don’t worry, if you don’t currently have an account, use this link and get $25 credit on DigitalOcean!
If you’re already an existing user, use your account and follow the steps listed below:
For a base configuration, use the following settings.
Here’s how it should look like:
Great! It will take a few minutes (approximately 3-4 minutes) to install Appsmith on the DigitalOcean droplet. After this, you’ll find the deployed droplet on your dashboard with all the details of the selected configuration.
Now, to use Appsmith, you’ll need to copy the IPv4 address from the settings and open it in a new tab. This will take you to Appsmith’s login page. You’ll have to sign up for a new account on Appsmith since it’s the first time you’ll be using it.
Follow the steps shown in this GIF:
To host the Appsmith DigitalOcean droplet on a custom domain, you’ll need to select the Add a domain option from the dashboard.
This will redirect you to a new page, where you’ll need to add your domain name. Once that’s done, it’ll give you records of the name servers. Copy the NS (name servers) details and use the custom name server’s configuration on your domain provider. Sometimes, it might take up to 24-48 hours for this to go live! Be patient 🙃
In this tutorial, we discussed how to deploy Appsmith on DigitalOcean. However, this is not the only way to use Appsmith; you can always self-host it on different cloud platforms. You can learn more about setting up Appsmith in different environments using these setup guides. Additionally, you can always migrate your applications from one environment to another using the import-export feature. To learn more about this, read the blog post here.
We hope you found this guide helpful! Your contributions and feedback help us make Appsmith better, and we really appreciate it.
Join the community! Come chat with us on Discord, or jump in on Github directly!
This week, we’re back to feature apps made by Appsmith’s newest team members! Each new team member has to make an app on Appsmith as part of the hazing welcoming ritual! 😬 We’re a fully remote distributed organization with colleagues in more than five countries, and this is a fun and educational way of onboarding new members onto the team. And of course, it makes sense for people working on making Appsmith better to use it, understand it, and know the framework’s shortcomings. These apps made during the onboarding process can range from functional to fun or straight-up silly!
This week, we’re featuring our colleague Ashit Rath’s app. Ashit is a Sr. Frontend Engineer from Bhubaneswar in India. He has experience in building scalable web applications, and he loves to travel. You can follow his work here.
Ashit decided to make a simple food nutrition app to list items, and it would show you the nutrition details. Ashit’s recipe analyzer is an excellent example of the range of applications you can make on Appsmith.
During the app-making process, Ashit found the following things great about Appsmith:
In the next part of the blog, Ashit has listed the steps to build the recipe analyzer.
This short tutorial uses the cloud version of Appsmith. However, you can always export and import Appsmith apps to different environments (cloud, self-hosted, local). The recommended way to use Appsmith is via Docker; follow the documentation here for detailed instructions if you want to build locally.
There are three parts to building this Recipe Analyzer app:
The API that we have used here comes from Edamam. They have a robust API for any kind of food/recipe/ingredient level search.
Sign up for their Nutrition Analysis API as a Developer account to try out without a subscription. The Developer account might give out less information than it should, but it should be fine for our use case.
Once signed up, we need to generate the API key from here.
We have the API key from the previous step, so now we will use that to make API calls to Edamam for our searches.
Now head over to Appsmith to create a data source.
https://api.edamam.com/api/nutrition-details?app_id=<application id>&app_key=<application key>
This should create our data source for fetching the nutrition data.
Let's create a new input and connect it to the data source to fetch.
This code basically takes the FoodInput text, modifies into proper API request format (array of string), stores the value in global storage using (setValue) and triggers the nutrition_api (nutrition_api.run)
That's it; we have connected our API and our form to send requests and get our awesome nutrition data!.
Now we create the part where we display the data from Edamam and show it in a neat format.
All of the data points are calculated in a similar fashion, so we will demonstrate the only one just to get the idea behind it.
Let's consider Total Fat, the value for it can be derived by having the following code in the text property.
This first checks if totalNutrients.FAT.quantity exists or not; if not, then we display "-.” If it exists, then parse the value and append the unit to it
So "10.12520" becomes 10.12 gm (gm comes from nutrition_api.data.totalNutrients.FAT.unit)
Similarly, the Total Fat Daily Percentage can be displayed using the same logic.
We build the whole UI by adding similar code but changing the key from FAT to whatever macro/micronutrient is required to be shown.
Wasn’t that simple?
This recipe analyzer can be used as part of the many tools a fitness company/studio can give its members. We took the recipe analyzer a few steps further and envisioned the various other things to help a fledgling fitness studio tech up.
See the screenshots below to get a better idea:
You can make a fully automated system to keep track of progress for clients, with our modal widget, you can automate payment collections etc. Just connect your data source to get started!
Connect your database from Airtable or Google Sheets and start building!
For a detailed tutorial on how to build dashboards and admin panels, follow this link.
Have you made something using Appsmith? Write to me (vishnupriya@appsmith.com), and I would love to feature you on our blog! If you’re interested in building an app on Appsmith, sign up today . We have docs, tutorials, and live help on our vibrant Discord community to help you along the way. So go ahead, put your ideas out there!
From startups to large multinational corporations, every organization needs a tool or an application to keep a track of expenses. These apps usually help different departments, for example, the CEO’s office or finance teams to keep track of salaries, reimbursements and other company expenses.
There are several tools that one can find to manage expenses, however, these are either expensive or lack some crucial features that do not serve a large number of use-cases and finance goals.
We think that building expense managers shouldn’t be too complicated. So, we built an expense management dashboard using Appsmith and Google Sheets, which can be used by an organisation to manage reimbursements expenses based on their monthly budget limitations. Additionally, admins of the app can also either approve or reject it based on the reimbursement request that is raised by an employee.
Here’s a sneak peek of what the app looks like.
Appsmith is an open-source framework that lets developers build dashboards, workflows, and CRUD apps with only the necessary code. You can connect to any API or databases like MongoDB, PostgreSQL, or MYSQL and get access to multiple widgets, including charts, tables and forms, for building a UI fast.
Following are the table of contents:
Follow the steps below to use Google Sheets with Appsmith:
Awesome! Now that our Google Sheets Plugin is set up, let’s create a new Google Sheet and add the necessary fields required for managing expenses.
Following are the fields we’ll be considering:
To make this more precise, we’ve made a sample Google Sheet with some mock data here. We’ll be using the same Sheet throughout this guide, and you can either follow with this or create your own based on our requirements.
docs.google.com/spreadsheets/d/1b7BuwDx0He4..
Now that we are connected to our Google Sheets data source, let’s connect to our Google Sheet and query all the data onto a list widget in Appsmith. To do this, navigate to the created data source under the APIs section and click on the New API button on the top right. Next, follow the below steps:
https://docs.google.com/spreadsheets/d/1b7BuwDx0He41wtKYazxX3uJyIgQDHDRWyfyycL6mLMk/edit#gid=0
Awesome, now that we have our data from the Google Sheet, let’s put this in a list; drag and drop a new table widget and paste the following in the Table Data property:
Quick Hack: For making the application more readable, let’s change the colour of the text based on the Reimbursement status. Appsmith allows us to write JS for styling widgets, now open the Text3 property pane and toggle JS in the text colour property and paste the following code:
With this, our list widget is colourful and feature-rich.
Here’s how it looks like:
In this section, we’ll create a new form that will allow users to post new reimbursement requests to the admins. For this, let’s use the Form and Input components and Google Sheets integration on Appsmith. Follow the below steps:
We’ll add the select widget onto the form to set the type of reimbursement. Open the property-pane of the select widget and let’s add the options by pasting the following code:
Here we define an array of all the options and iterate through a for-loop and render them all in the select widget.
Now that we have our form ready, let's write the logic to push the values from the form to the Google Sheet whenever submitted. Follow the below steps:
Here, the keys are the column names in the Google Sheet, and the values associated with them are the names of the input widgets. The .text method is used to pick the text that's written in the input widgets.
Lastly, in the form below for the submit button, set the on click property to Call an API and call the postReimbursement query from the options. With this, we should be able to add new rows to Google Sheet from Appsmith.
In the next section, we will build an Admin Dashboard where admins can approve or reject the requested reimbursement.
The expense manager admin can be only viewed by the admins of the application. Here we’ll be displaying all the information regarding the reimbursement’s and add an option to approve and reject them with a comment.
To build this, follow the steps below:
With this, we should see all the reimbursement requests with pending status on the table widget. Now, add to add options to approve and reject follow the below steps:
Now create a new API from the Sheets Expense Manager data source and rename it to aprroveReimbursement, the idea here is to update the status of reimbursement whenever the approve button is hit on the Table. Now, in the query set the method to Update sheet row and row object to the following:
Similarly, create another query for rejecting the reimbursement (rejectReimbursement), use the following code snippet in the Row Object property:
Now, go back to the Table Widget, and set the Approve button onClick property to execute a query and select the aprroveReimbursement query.
For rejecting the query select the rejectReimbursement on the Reject button’s onClick property.
Similarly, add two more tables to show all the approved and rejected reimbursement for future references, drag and drop two table widget’s and set the Table Data to the following:
Table2, Table Data:
Add some additional metrics to track expenses!
Our dashboard is almost ready, now to give the admins an overall picture of expenses, let’s add some metrics that’ll help quickly look at the pending, paid, and rejected amounts. For this, we’ll need to drag and drop the text widgets and use the following snippet to do the calculations from the table widget.
In this code snippet, we’re iterating over the Table1 data and counting the summing up the Amount column. As the text widget accepts a string, the function will be returning the same data type. Similarly, let’s drop two more text widget’s and calculate the total amount approved and total amount rejected.
Use the following snippets:
Total Amount Pending
Text Widget Value:
Total Amount Rejected
Now, finally, this is how the admin view looks like:
Building this app from scratch, including writing snippets of code is likely to take 30 minutes! Isn’t that simple?
If you liked this tutorial, and are planning to build this, let me know. I’d love to help you make it as complex as you’d like. Write to me at vihar@appsmith.com
An admin panel usually refers to the set of tools available to the administrator of a web application for overseeing the app. The administrator is usually an owner or superuser who has permission to create, edit and delete certain components of a web page normally hidden from a regular user. The admin panel usually provides all the settings and tools used for system administration.
It’s not uncommon for web apps with sophisticated, complex, and beautiful user interfaces to have pretty bland admin panels. This is because the admin panel is hidden from the app's primary users and usually isn’t considered a priority. They’re also not very much fun to build because of the amount of repetitive work that goes into creating one.
In cases like this, developers would benefit from a tool that makes the process of building an admin panel easy without the need to write code. This would of course drastically reduce the amount of time and number of developers needed to work on building the admin panel. This is where Appsmith comes in.
Appsmith is an open-source framework that helps developers build dashboards, workflows, pages, and CRUD apps with little to no code. You can connect to APIs or databases like MongoDB, PostgreSQL, or MYSQL, as well as get access to charts, widgets, and other customization tools for building a UI.
In this article, you’ll learn how to set up Appsmith locally. You’ll create a new application, connect an API to it, and build an example admin panel using widgets and pages.
To begin, you'll need to sign up for Appsmith (it's free!), if you don’t already have an account. You can also deploy a Docker image on a server. For the purposes of this tutorial, you’re going to create a local instance of Appsmith using Docker.
To work with Appsmith, you need a data source. This can be in the form of an API or a database. Appsmith supports MongoDB, MySQL, and PostgreSQL among others.
For the purposes of this guide, we'll connect to a fake API service called JSON Placeholder.
Go to the previously created page All Posts. On this page, you’ll display a list of posts on a table using the Table Widget.
Now you should see all of the posts on the table, with their respective columns and rows. The table comes with filtering, pagination, sorting, and a search bar.
Next, add a button that will create a new post. Once the button is clicked, you want it to open a new page that contains a form for creating a new post.
In this section, you’ll create a New Post page.
In this section, you'll see how to configure the application to add and delete records using the fake API.
The form has two buttons at the bottom that controls how the form works:
To configure Submit to submit the form data, follow these steps:
Define the API that adds posts in this section by doing the following:
In the above sample, new_post_form refers to the form you created in the New Post page, while .data refers to the form's filled-in values.
Appsmith allows you to access all the data on the form by referring to the widget's unique name. To see the data being sent:
You've now configured the form's Submit button to call the create_post API when the form is submitted. You can also define the action to take after submission. To do this:
To demonstrate how to delete a post using the Appsmith tools, go to the All Posts page and add a Delete button to the last column of the post_table:
Let's define a new API called delete_post.
Clicking the Delete button would send an API request using delete_post and then show the success message.
Of course, the selected post does not really delete since we’re using a fake API. But it does demonstrate how you would configure deletion with a real API on an admin panel.
You've seen how easy it is to build an application on Appsmith, specifically an admin panel. This guide covered how to create an application and connect it to a database, as well as how to add and delete data. You learned how to build interactive pages, work with widgets, and customize them for your purposes.
Building an admin panel with Appsmith is a fast way to build admin tools. Check it out if you’d like to save your developers time and get internal tools launched faster.
Author Bio: Adeyinka is a software engineer based in Lagos, Nigeria, currently at BriteCore. She loves researching and writing in-depth technical content.
I recently joined Appsmith, and I am one of the few non-technical employees here! And as part of the onboarding process, all new team members have to build an app on Appsmith! It doesn’t matter if you’ve studied journalism and anthropology, have no experience in coding or JavaScript, no excuses! The brief was that it could be fun or functional, and anything under the Sun! Anxiety and panic were having a field day while I thought about what to build and where to start and finally decided on making something fun yet functional for Appsmith.
We have a vibrant channel on Slack called the #reading-club, where channel members can share and discuss books they have read. I expect (and hope) that this channel will have a high volume of messages, and the members are likely to grow. Even though there are only 26 members in the channel right now, one has to scroll up to get to earlier recommendations! It can be pretty frustrating to do all that when you’re not checking the channel every day, and it can be confusing to go through different recommendations by different members. The channel is a great way to share your thoughts, but there is no way of organizing those by name. To this end, I created the Appsmith Reading Club App, and here’s what I hoped it would do:
To build the app, here’s what I did:
As a 'visual person,' and I feel most comfortable mapping out the elements and figuring out a flow. It helps me get a clear idea about what each component looks like and sets the scope.
I wanted one part of the app to be a list of names of the channel members, a button that could filter out their messages and display them in chronological order. Here are the widgets I used to build my UI. It took me under 10 minutes to put this together.
It's the next steps which are unfamiliar for a non-technical user like me: connecting a data source, writing code, and ensuring my app works! For this part, I enlisted my colleague, Vihar's help.
Here's a short tutorial!
To pull information from a channel on Slack you need to work with the Slack API.
You have to then create an app and then generate OAuth tokens; to be able to do this, you need admin access to your organization’s Slack.
Here’s what our oauth configuration looks like:
Next up, you have to link this configuration to your Appsmith application. This short tutorial uses the cloud version of Appsmith. However, you can always export and import Appsmith apps to different environments (cloud, self-hosted, local). The recommended way to use Appsmith is to use Docker; follow the documentation here for detailed instructions if you want to build locally.
In the next step, you will connect to the Slack API that will return all the users from the entire organisation. Since this is a secured API, we need to use the bearer token from the slack developer application to use it.
Follow the steps listed below:
Now in the response pane, you should be able to see all the users from the Slack organization. However, since our goal is only to fetch the users from a particular slack channel; in my case, this was #reading-club. For this, you have to write one more API that fetches details of a specific slack channel.
To do this, follow these steps:
Here, as you can see, we’ve sent an additional parameter, which is channel-id. You can find this by clicking the details of the slack channel.
Now, to fetch all the messages from the slack channel, create a new query called getMessages. Follow the same steps, and replace the endpoint with the following:
Here, you can limit the number of messages by sending an additional limit parameter. Now that we have everything, you can start building the UI for the app.
First step is to show all the members of the slack channel using a Table widget; when clicked, it will show all the book suggestions and other messages on a different List widget.
Follow these steps:
In this snippet, we first fetched profiles of all the members in the slack organization and filtered them by user_ids with the selected slack channel. You can use a map function to return all the details of the users.
Next, we configure columns in the table by clicking on the cog icon for each column. For example, to render images from the API, we’ll need to access the profile key. Hence, we set the column type to image and set the column computed value to the following:
With all the connections in place, the application will be fully functional. To take a look at my app, click here
It took me approximately 30-40 minutes to make this! My next steps would be to refine this app and add a few more elements, for example, displaying the date and time the messages were sent, images, and replies, filtering out system-generated messages, etc. While my experiments with Appsmith and this world of low code tools may have started with my soft spot for books, I quickly thought of other use-cases that can be implemented via the same app, such as automating other critical conversations/task-management on Slack channels or any other messaging applications. These would make my day-to-day job much easier! :)
It’s a pity that the world of internal apps is not given due attention simply because it’s not always customer-facing. Shifting our perspective to consider all users as customers can be a significant first step in building great internal apps. And low code is the future — internal applications can be tailor-made in a fraction of the time and cost while helping businesses focus on what matters most to their growth.
I love hearing from our users and contributors. If you’re interested in building something on Appsmith or are currently building something, I'd love to pick your brain, please email me: vishnupriya@appsmith.com
Hey everyone! Joseph here from GreenFlux, LLC. I'm a Shopify Partner Developer and a HUGE fan of Appsmith! 😻
In fact, I've written several blog posts on Appsmith integrations already, but today will be my first post officially written for Appsmith! I'm super excited to be working with the Appsmith team and sharing my API integration experience with the community.
I've done a lot of work with the Shopify API over the last few years, but only recently discovered Appsmith. So I wanted to put together this guide with some specific use-cases that help solve some common business problems.
but before I get to those specific use-cases...
The Authentication steps may be different, but most of this guide will work with any API to:
Most shops only take orders for products that they have in inventory, then ship them out as the orders come in. But some businesses wait to begin 'creating' the product until an order has been placed. Think T-shirt printing, custom-built bikes/skateboards, and even wholesale produce and flowers that are only harvested after an order is placed.
That creation/ harvest process can have several steps and require multiple employees, and even have an approval process with different access levels. Lots of industries are creating products to-order, and need a way to track this process without sharing the Shopify admin login to all users.
And you have a team of workers in three departments:
[Assembly, Quality Control, Shipping]
Start by creating a Google Sheet for Workers and another for Assignments. Or you can copy this public sample sheet .
Ok, on to Appsmith
4. Set Authentication Type to Basic
Next let's create our first query to GET orders.
Awesome! Our new app is now making authenticated API calls to Shopify and returning data.
Copy the API and rename get_products, then change orders to products in the endpoint URL.
Next, let's add a few widgets to display the data
Alright, now to connect the Google Sheet data.
If this is your first time connecting Google Sheets to Appsmith, start out by adding a new datasource:
Datasources + > Create New > Google Sheets
Appsmith Docs
Then follow the prompts and authorize Appsmith to connect to your Google account.
Next, copy the get_workers API, rename get_assignments and change the sheet name.
Ok, so far we have GET requests working to Shopify and Google Sheets.
Go ahead and add a few more Table Widgets for Workers and Assignments using the same method above.
Now we need a way to feed the get_orders request to the orders sheet.
Appsmith has a full list of methods available for performing CRUD operations with Google Sheets. We could use Insert sheet row to add orders one at a time, but the get_orders API returns an array of orders.
Now, the Bulk Insert Rows method expects an array of objects, with keys that match the the sheet's column names:
And the map() method returns an array.
So we can map()! over the get_orders data and build our rows.
Detailed explanation here: blog.greenflux.us/saving-api-response-data-..
4. RUN 🚀
But what happens when we run it again?
Uhhh... now I have two copies of every order.
Hmm... we need a way to tell Shopify what orders we already have, and only download new ones!
Here's where things get interesting. First we have to get_assignments, then find the max order number that's already in our sheet, and finally, send a new request to Shopify to get new orders after that order number.
We can use the since_id parameter to filter the orders that are returned and then save only new orders back to the sheet.
First we need to know the last order number from our sheet. I like to store these values into a separate widget, so I can reference just the name, instead of trying to insert a whole function in place of the ID in the URL.
3. Update the get_orders API endpoint
This will produce an array of all order ids, and then sort them in case any of the rows are stored out of order in the sheet. The default sort order is low to high, so reversing and taking the first (zero index [0]) item returns the max value.
Now we're getting somewhere. We can continuously download orders to the order sheet, but what about updating individual rows?
First let's add a few Widgets to view/edit the selected assignment. I've added a Container Widget to the right of the table_assignments, Text Widgets to display the Order# and Products, and Input Widgets for the Worker and Instructions.
Now we can reference the table_assignments.selectedRow properties to populate the default values for our Widgets. This will update the Widgets automatically when the selected row is changed.
Next, let's add a few Widgets to set values in the assignment sheet.
First we want to add a Select Widget (dropdown menu) with all the workers. The Options should contain an array of objects with label and value properties. (literal array, or expression that returns an array).
So you could hard-code the Select Widget's Options:
...but wouldn't it be cool if our dropdown could automatically show all the current workers from our workers sheet?!
Time to test out these new input fields!
{dividerUpdate a row in Google Sheets
NOTE: I removed the id and products because these should not be edited once downloaded. Our template is only for updating the worker_id and associated timestamps/ instructions.
Ok, we're almost there! The last piece we need is a way to fulfill an order in Shopify.
NOTE: Orders can have multiple fulfillments per line item and different status for each fulfillment. To keep this example simple, our app is going to create a single fulfillment per order and ignore partial fulfillments.
This step will be using the /fulfillments.json endpoint, and we need the location id. You can get this through the API, but the easiest way is to view the location and get the id from the URL.
We want the employees to be able to select a row in the app and click 'Fulfill Order' without giving them full access to the Shopify admin account.
In other words, we want to use data from the selectedRow of the table_assignments to send a POST request to Shopify.
3.Set the body to:
4. Add a button to run the create_fulfillment API
Thanks for taking this journey with me on my first official Appsmith post!
This is just a small sample of the awesome power of Appsmith. There's so much more we could do from here, like connecting another API and sending Slack messages or emails to each worker when an order is assigned, emailing customers pictures of the products during production, or calculating average processing times per worker or product.
Many companies and organizations rely on internal dashboards or admin panels that are connected with different data sources. In this guide, you’ll learn how to integrate a MongoDB data source with Appsmith and build creative dashboards.
Usually, building an admin interface over MongoDB is a time taking process and a lot of configuration has to be made. Also, for database management, schemas and queries have to be maintained on a different platform. While the UI client would be needing one more server. But with Appsmith, you can have everything under one roof and you can build UI within no time. Let’s see how by connecting to MongoDB on Appsmith. Below is a screenshot of how our dashboard is going to look like:
If you prefer a video tutorial, check out our video on How to Build a MongoDB Admin Panel in 5 Minutes!
Usually, MongoDB clusters are hosted on the cloud. Now let’s connect to one of the example clusters that’s on MongoDB cloud and list out all the data that’s present inside the database.
"The database we’ve worked on is a collection of product and sales information. You can find the finished admin panel app here."
You have your data-source connected, and also a query that can fetch all the product items for you. Now, let’s put these on a table and render all the data. To do this, you’ll have to navigate to the Page, find the Table Component under the Widgets section, drag and drop it to the canvas. Next, open the table’s property pane by clicking on the cog-wheel on the table. Now under the Table Data property, add the following snippet:
Here, you’re using the get_products DB query and rendering the data from it onto a table.
"Appsmith allows us to parse javascript using the moustache syntax {{ }}."
Not just reading data, with Appsith you can perform all CRUD operations on the MongoDB. Now on our dashboard/page let’s create a form that allows us to update any selected value on the table.
To build this form, we’ll need to drag over a form widget, a bunch of text widgets, an input widget, and a date picker widget to the canvas. The form should look like this after setting up the UI:
Once we have the form setup, we would need to link the form to the table so that when a product is clicked on the table, the corresponding information is pre-filled on the form.
Appsmith provides us with an easy way to hook into a widget’s state. You can configure the text widget to show the name of the product selected on the table by setting its Text property to:
You can do the same for the date picker and input widget so that the default text is set based on the item clicked on the products table. For example:
Also, don’t forget to set the Data Type of the input widget to Number.
Lastly, you’ll need to write a query that grabs data from the form and updates the product selected on the table when the submit button is clicked. To set this up, click on the cogwheel on the submit button. Then set the onClick to execute a DB query and then click on create a query:
Let’s call this query update_product and configure it this way:
The update_product query shown above updates the item with _id selected on the table with quantity and expires_at gotten from the input and date picker widgets. Clicking the submit button on the form triggers this query.
You’ll now have a functional dashboard that displays product information with a form that allows us to update an individual product.
Additionally, you can display data using charts. We have a sales collection that lists sales data of a particular product. It’s a good idea to display this data in a chart.
To build this functionality, we need to go back to the table widget and configure the onRowSelected action to execute a DB query and then, click on create a new query.
Let’s name this query get_product_sales and configure it like this:
The above query filters sales information on the sales collection for the product with the _id selected on the table. Also, this query will run whenever a row is selected on the table.
Lastly, we need to display the data from this query in a chart widget. So drag in a chart widget and configure the Chart Data to be:
And we can see the chart widget re-rendered with the sales data for the selected product on the table. You can go ahead and tweak the widget as you see fit.
To deploy the admin panel, hit the deploy button at the top right corner. You can share the admin panel by clicking the share button and toggling the switch to make it public or only invite people you want to have access to the app (i.e people in your organization) via email.
Kudos! Your admin panel is now up and running!
with inputs from Confidence Okoghenun
We've been a long-time Calendly user, an app that lets others block our time and schedules meetings. And we love how much time it saves me. But we've needed a few additional features that were only available on their premium plans. Instead of upgrading it, we've decided to build our own that can be easy to use and fully customisable!
Unfortunately, there's one problem here. We'll have to pick technologies, write lots of code, build UI, deploy them from scratch. Which is again time-consuming. To skip all of these, we used Appsmith for the UI, APIs by Google Calendar and Zoom for video-call services.
"✨ Appsmith is a cloud or self-hosted open-source platform to build admin panels, CRUD apps and workflows. With Appsmith, you can build everything you need 10x faster. ✨ "
You can build this, too, in just under 30 minutes! Click here to try. Block the time for a live demo. Here's a quick sketch of what we'll be going through in this guide:
Let’s get started!
Our first task is to connect our Google Calendar and list down all our calendar events. For this, we’ll have to use Google APIs and OAuth authorization to authenticate the user from Appsmith.
If you're an existing user, you can sign in to Appsmith or sign up for a new one (it's free!). We’ll walk through different steps to list our events!
Awesome! We've now had the authorization to access our google calendar.
Our next step is to create an Appsmith App and fetch all the calendar events.
Let’s create an API to fetch events from our calendar and call it fetch_calendar_events. Use the following CURL command:
Let's make these parameters dynamic by adding some javascript. To do this, we'll use Javascript and moment.js, both of which can be used in Appsmith by writing {{ }} in any field.
Now replace the placeholders with the above js snippets and hit run to fetch your calendar events! Below is a screenshot explaining the same.
Awesome! This will now display all your calendar events.
Now that we have all the events from our calendars, we need to build a UI to display these events. Appsmith has a simply DnD interface to build UI. We can use the Table to display our events, a date picker to select which day we should fetch events for, and a dropdown to select the meeting duration we'd like our users to schedule. My UI looks like this, but you can get creative and built something that feels intuitive to you. Be sure to name your widgets well. The naming I'm following in this post is
With an idea of the layout and inputs we need, we can configure our Table to display the events our API is returning using JS. Now, set the table data to : {{fetch_calendar_events.data.items}}
Now, this is how our app should look like:
No surprise our table doesn't look very readable because APIs are rarely built to work with views out of the box! Now with a little Javascript, we can transform the ugly API response into something human-readable and add some logic to show us the free slots instead of the calendar event. The following code goes into the table data property of the eventsTable.
The above logic was really the hardest part of building this application and took the longest to get right (but also the most fun part). The code declares a self-invoking function that iterates over the response of the fetch_calendar_events API and adds free time slots to array slots that are returned by the function. It begins iterating from 10 am to 8 pm (again hardcoding my workday for convenience) and uses the value in the durationDropdown to determine the number of free slots of selected duration that can fit between the current available time and the next calendar event. It then skips to the end of the next busy calendar event and continues this till it reaches the end of my workday!
To schedule a meeting, we can create a button on the table and configure it to open a modal once it is clicked. The modal UI can also be custom-built using DnD to capture a user's name, email, and purpose of the meeting.
Name the inputs as nameInput, emailInput and purposeInput so we're able to use them in our API. Let's import the following CURL and name the API create_event:
In the above API, we need to accept dynamic values from our app, so we need to replace some of the params and headers.
_USERNAME:
_STARTTIME:
_ENDTIME:
DESCRIPTION:
TITLE:
EMAIL:
With this, our API is reading values from the eventsTable and the slotDatePicker to create the right event for the selected slot (eventsTable.selectedRow). We can now bind the onClick of the confirm button to call the create_event API and close the modal onSuccess.
Finally, there's one more thing. We need to send out a Zoom link for every event to integrate Zoom's APIs and create a zoom link for the calendar events. (This is one of the things I love about Calendly) To integrate with zoom, we have to fetch a JWT to authenticate our application requests with zoom. We'll follow this guide. With a JWT in hand, it became as easy as importing another CURL and naming it create_zoom.
Replace the following variables as shown:
JWT with your JWT token
TOPIC:
STARTTIME:
-DURATION:_
We also have to update our create_event API to save the zoom link returned by this API in the calendar event. Update the description field to
Now let's call our create_zoom API before we call create_event and close the modal. To do this, we can easily convert the onClick configuration to javascript and write a neat little workflow using callbacks.
Now hit deploy, make your application URL public by clicking the share button, and share it with anyone you need to meet. You can try my meeting scheduler here. Soon we’ll be having a fork app feature on Appsmith so that we can directly fork this one and customise accordingly within no time. All we’ll have to do is update the forked app with the new API keys.
If you like what we've built, star our ⭐️ Github Repo. Also, we’re an open-source company.
Also, do let us know your thoughts on this article in the comments section.
Waitlists are a powerful way to test your app or feature with a small group of users.
In this guide, we’ll build a waitlist manager that integrates with a SQL DB to provide access control. If you are new to Appsmith, read about Appsmith's core concepts before following this guide.
Our app will access data from a MySQL DB that stores all user data.
The application consists of 3 pages: A dashboard that lists a few useful metrics, an Add users page, and a Manage Users page. The 3 pages will be powered by 7 queries.
This guide will walk you through the structure of the database & the queries used. It won’t dive deeper into how the product will access this data. We assume your product can already talk to your backend, if not you can build APIs using solutions like PostgREST or build your own with NodeJS, Express & Sequelize.
This uses a Mysql DB with a single table, Users, as described below.
This application requires seven queries listed below.
List All users Rather than running a select(*) we are listing all columns with human-friendly names. Query:
This insert query adds users to the waitlist and sets enable_beta & logging to false. The function NOW() set Created_at & Updated_at to the current date. You can modify this behavior if needed.
This query updates all the properties of the user based on the update form. This dynamic query sets the status of from_version_code to the given value if enabled_beta is set to true, else from_version_code is set to null. The updated_at column is set to NOW() to capture the date of the update.
This query provides the number of users per beta version
This set of 3 queries will help us build a set of KPIs to monitor:
This page is a form with two input fields, for the user’s name and email address. On submit, we add the user to our database using the Add_User query.
To make sure the user is entering a valid email, we set the field type to email.
This page is the workhorse of this application. The table widget lists all the users and the form updates the user details & permissions for the selected user.
The page is dynamically modified based on certain states.
1. To provide a better user experience, The form is hidden when the table does not have a row selected. To hide the form, set the Visible JS property to
2. The “Beta Enabled” dropdown disables the “Beta Version” field when set to No.
To achieve this, set the Disabled JS property to
as shown below.
Finally, we connect the update button to the update_user query.
Set the onSuccess property of the form to run the All_users query to refresh the table on any modifications.
This page provides the following metrics.
For the three metrics, connect the three labels to the three aggregation queries listed above. Unlike a table, setting a label to the result of the query needs to point to a single value rather than an Array. Here it is set to {{kpi_count.data[0].count}} as the queries will always return a single row and a single column named count.
Finally, add a table and connect it to the List Users By Version query described above.
This completes the application. You can deploy the application by clicking on the deploy link on the top right. Once deployed, it will be visible to everyone in your organization.
For more details on sharing, you can refer to the Access control documentation.
You can play around with it using the link provided below. A few possible extensions are also listed below for you to try out.
Demo Application
You can try the application out here.
As an exercise, you can clone the application and try to extend it. Here are some possible directions you can take.
Control more features by adding more columns. For example add an Enable_Premium column, to give the user access to premium features.
A possible larger refactor of this application is moving the features out of the Users table. The sample table diagram below shows a possible structure.
This enables the addition of another form to add new features if needed.
Since we are capturing the creation date of users, you can add a chart that shows the number of new users added each day.
Making the Add users form public allows users to direct join the waitlist. The best way to do this would be to create a separate application with just the Add users form.