Search

Reinhart Previano K.

Do you love to Ctrl-K, Ctrl-/, or / ? Now you can do three of them (>_ )!

No results so far...

Contact Information

Blog posts from the feed-en-tech channel (@feed-en-tech)


Site and Infrastructure updates, September 2024 edition.

Hello, world! We’re currently in the middle of something great, and we can’t wait to finally tell about that. And at the meantime, here’s what’s new and improved in our website. 1. We’re making (https://)shiftine.sh. What could that really be? Reinhart personally wanted to relocate our fandom from reinhart1010.id to shiftine.sh, stuffed with command-line easter eggs that fits with our new website name (.sh is also a file extension for shell scripts). But we still need a lot of time to finally ship that to you. Well, queue and jump in to the happiest website that (we’ve) ever shipped! 2. We’re also remaking our color palette website. Our color palette website is currently being rewritten from scratch, this time using Remix and Cloudflare Pages. We’re almost done with Codepen who have helped hosted our color palette website for almost two years, and had blocked our login attempts for months due to a then-ongoing DDoS issue. And we’re rebuilding our codebase to be able to export our color scheme into a number of apps and design systems. That would make us easier to make and share our custom themes for your favorite apps, from Firefox to Visual Studio Code. 3. We’ve upgraded our website to Laravel 11. This is nothing exciting for most people, but hey, we’re still taking care of updating our website libraries for the better. 4. We fixed a Dark Mode bug. Starting today, when you visit our website, we will always set a new cookie named r10-current-auto-theme to fix an annoying Flash of Unstyled Content (FOUC) bug as we changed how our Dark Mode was implemented to support our new 404 webpage (introduced July 2024). We can point you to the exact source code on GitHub where we set and use those cookies. This feature is GDPR-safe as those cookies are made for functional and UX purposes. 5. Search result now include dates. Finally, and finally (this is the last update we’d like to announce for good), we’ve improved our search results a bit by adding timestamps, the date and time where those articles are originally published (not updated). The date and time should be adjusted to your local time settings, so no need to figure out your time from UTC or Asia/Jakarta. So that’s all for now. Welcome to MY world (>_ )!

How to properly update your WhatsApp Business account name with Cloud API.

This tutorial requires the use of the command-line interface. For Windows, we recommend instead to use PowerShell instead of the Command Prompt. Warning: There are three different dashboards to interact with WhatsApp Business Platform. For the purpose of clarity, here's what we really meant about: Meta App Dashboard (formerly Facebook Developers App Dashboard): https://developers.facebook.com/apps Meta Business Suite (formerly Facebook Business): https://business.facebook.com/latest/home WhatsApp Manager: https://business.facebook.com/wa/manage The WhatsApp Business platform also consists of different set of credentials as listed below. Here, we only need to use the Access Token, the WhatsApp Phone Number ID (not the Business Account ID), and the WhatsApp Two-Step Verification PIN (more on that later). Access Token: In order to perform HTTP request to WhatsApp Business Platform. The Meta App Dashboard by default allows you to create temporary tokens for use in 24 hours. To create a permanent access token: Ensure that your Facebook account is connected to both the Meta Business Suite (to manage business entities) and Meta App Dashboard (i.e. by registering into the Meta/Facebook Developers programme). Register a new business and Business Assets (i.e. related Facebook pages and Instagram accounts) on Meta Business Suite. Register a new app on Meta App Dashboard Create a new System User on the Business Settings in the Meta Business Suite On the Meta Business Suite, create the Access Token by clicking on Generate Token button on the System User settings, then link them to the desired App. App Secret (as configured in the App Dashboard): Only useful when authenticating received webhooks. Webhook Verify Token: A unique token set by you to be able to verify certain webhook events. WhatsApp Business Account ID: The Facebook Graph API Object ID representing the business account. This ID can be easily grabbed on the Meta App Dashboard, assuming that you have registered the phone number. WhatsApp Phone Number ID: The Facebook Graph API Object ID representing the registered phone number. This ID can be easily grabbed on the Meta App Dashboard, assuming that you have registered the phone number. WhatsApp Two-Step Verification PIN: A 6-digit PIN set by you to secure your WhatsApp business account. If you are not familiar, the Facebook Graph API introduced an universal ID format for every kinds of object/entities. That means if there is a WhatsApp Business Account ID of 123123123, then it is guaranteed that the number are not used in any other forms of objects, like the WhatsApp Phone Number ID, the Facebook Pages ID, the Instagram Post ID, and so on. Step 1: Request a display name change on WhatsApp Manager. You cannot try this feature on the default Test WhatsApp Business Account or any account that has the Display Name change featured disabled for administrative reasons. Go to WhatsApp Manager > Account Tools > Phone Numbers. Make sure that you are selecting the correct WhatsApp Account on the top-right corner. You can also see that there's the "WhatsApp account ID", which is actually your WhatsApp Business Account ID. It is different than WhatsApp Phone Number ID that we need later, as some WhatsApp Business Account are allowed to add more than one phone numbers. Now, on your desired phone number, change the display name. You can only move to the next step if the new display name is approved. Step 2: Set up (or update) your WhatsApp Two-Step Verification PIN. This is the part where we start to use the command-line. If you never set up those PINs, you can send a request to the WhatsApp Business Cloud API: Replace the {{ACCESS_TOKEN}}, {{PHONE_NUMBER_ID}} and {{PIN}} with the Access Token, WhatsApp Phone Number ID, and WhatsApp Two-Step Verification PIN respectively. # Windows (requires PowerShell) Invoke-WebRequest -Method Post -Body '{ "pin": "{{PIN}}" } -Headers @{ Authorization = "Bearer {{ACCESS_TOKEN}}" } -ContentType 'application/json' https://graph.facebook.com/v20.0/{{PHONE_NUMBER_ID}} # macOS and Linux (requires curl) curl -X POST 'https://graph.facebook.com/v20.0/{{PHONE_NUMBER_ID}}' -H 'Authorization: Bearer {{ACCESS_TOKEN}}' -H 'Content-Type: application/json' -d '{"pin" : "{{PIN}}"}' Note: We recommend to use the System User Access Token instead of the temporary token generated from the Meta App Dashboard. Make sure that the server responds with {"success":true}. Step 3: Trigger the display name change on the WhatsApp Cloud API. Lastly, we can trigger the following command to apply the display name change. Replace the {{ACCESS_TOKEN}}, {{PHONE_NUMBER_ID}} and {{PIN}} with the Access Token, WhatsApp Phone Number ID, and WhatsApp Two-Step Verification PIN respectively. # Windows (requires PowerShell) Invoke-WebRequest -Method Post -Body '{ "messaging_product": "whatsapp", "pin": "{{PIN}}" } -Headers @{ Authorization = "Bearer {{ACCESS_TOKEN}}" } -ContentType 'application/json' https://graph.facebook.com/v20.0/{{PHONE_NUMBER_ID}}/register # macOS and Linux (requires curl) curl 'https://graph.facebook.com/v20.0/{{PHONE_NUMBER_ID}}/register' -H 'Content-Type: application/json' -H 'Authorization: Bearer {{ACCESS_TOKEN}}' -d '{ "messaging_product": "whatsapp", "pin": "{{PIN}}" }' Make sure that the server responds with {"success":true}.

Fing now won’t let me scan without giving my money, so I forked an old Android app for that (Altia).
Cover image for Fing now won’t let me scan without giving my money, so I forked an old Android app for that (Altia).
Firefox have just ended this annoying popup.
Cover image for Firefox have just ended this annoying popup.
Our guide to data models is here!

Last month, we explained on how we commonly design our REST API for our products. But apparently, some people still don't understand what the “model-centric path approach” actually mean. Now, we admit that it might be technical to explain here. In short, we are talking about data models, aka. how we commonly organize different sets of data. Since we all believe in object-oriented (OOP) software design, as well as object-relationship mapping (ORM) mechanisms, we adopt a strategy where a data model should be designated as a distinct Class (in OOP) and Entity (in entities, commonly in relational database design). Today, we are starting a new experiment on our digital garden. As we discussed last year, a digital garden is another way to organize ever-growing knowledge without forcefully having it to be perfect to be, a blog article, for example. And sure, there are some “plants” there that are more mature than others, and our explanation of Data Models could be one of them. When we talk about a data model, we’re not talking about one specific kind of data, but a group of data assigned according to a related context. It means that each data contained inside a data model should be related in a certain way. And that also means, data models are an efficient way to organize data to produce an information. Data Models on our digital garden. Now, no matter how deep are your current understanding about data, OOP, database systems, or so, we are trying our best to explain these concepts from beginners and up. So, why not just check it out at https://shift.reinhart1010.id/note/data-models?

HAM v1.1: Supporting tables and technical diagrams!

The version 1.1.0 was quickly withdrawn due to issues loading with custom tables HAM, our homegrown static Jekyll wiki framework now just got an update. Just like our past versions, this one is heavily motivated by our internal projects that are using HAM. With this new version, you can now render diagrams with Mermaid. Mermaid is an open-source language and engine that lets you render technical charts and graphs from plaintext, just like Markdown for rich text. Mermaid has been used in some notable Markdown-based apps that we personally love, including Joplin and GitHub. However, for the time being, we currently only support Mermaid when embedded inside a <pre class="mermaid"> HTML tag, instead of ```mermaid (as an annotated Markdown code block). The latter may clash with our existing syntax highlighting feature powered by Highlight.js. In our digital garden, we use Mermaid to render Entity Relationship Diagrams (ERDs) and Unified Modeling Language (UML) diagrams. And lastly, we also decided to add support for tables, just like our main website! If you have previously used other table markups, like the ones offered in Bootstrap 5, you will need to opt out from default styling by adding a special data- property, i.e. <table data-ham-ignore="true">.

Introducing HAM v1.0.4.

HAM is a simple Jekyll framework that allows you to build static wiki sites. And today, we are introducing a maintenance update with the following changes. First, the Bootstrap Icons dependency was updated from v1.11.1 to v1.11.3. There are no significant changes from the 100+ new icons introduced since v1.10. These icons are directly built into HAM, and you can simply use them in your Markdown source files as <i> HTML tags. (Just make sure you have reviewed their Web Accessibility recommendations on placing icons.) Next, we have also fixed a bug on v1.0.0 where users are redirected to the wrong YouTube URL when their web browsers do not support <iframe>. Well now, all modern web browsers supports that feature, and we're making this change to ensure that . HAM is not going anyway sooner. We still love HAM, and still use them on some of our internal projects. In fact, HAM still looks very nice on building another API documentation website like this: Of course, there are still some work to do. At least, readjusting the heading texts and adding more Liquid tags, and making these ugly tables more beautiful just what we recently did on our main website. So don't worry, we're still dogfooding HAM on our own.

Site Update: More glass-cards!
Cover image for Site Update: More glass-cards!
Our guide to our unwritten REST API conventions.

An updated version of this may be available on our digital garden. Naming things is a difficult thing, according to many developers. But not for someone who graduated in an university that’s silently houses great REST API experts. I’m not joking. According to HackerRank in 2021, BINUS University entered the top charts for Asia-Pacific universities (outside of India) according to their technical skills. And how did the university became the top 2 in REST API design, right after Rajshashi University of Engineering and Technology? Source: HackerRank, 2021. 1. Use semantic REST naming scheme. I know, there’s no such a standard term for “semantic REST API” like how it did with HTML, but there’s also a reason why HTTP requests are divided into GET and POST, which then added by PUT, PATCH, DELETE, OPTIONS, and others. We commonly use nested model-centric path approach, where the REST endpoint paths should be named after the model. No, we don’t mean GET /api/get-embed-from-post, but as straightforward as GET /api/posts/embed. Using the /posts/ prefix signifies the endpoint belong to the posts model. The model name must be referenced in their plural form. We first encountered this model-centric approach in Laravel, where controllers (as in the Model-View-Controller / MVC structure) are mapped into an opinionated set of REST request verbs (e.g. GET, POST) and paths. Taking from Laravel’s own example, we decided to define a similar schema: VerbURIDescriptionGET/photosGet an index listing of photos. Get (all) current photos. Can also be potentially used to search for photos.POST/photosSubmit a new photo.GET/photos/{id}Show a specific photo by its (internal) ID.PUT/PATCH/photos/{id}Update the photo information.DELETE/photos/{id}Delete the photo. You may also notice that some endpoints are not listed here. They are commonly used to display the front-end instead of doing the back-end logic. For example, GET /photos/{id}/edit does not edit the actual photo. It only shows a webform to the user, whereas the PUT/PATCH /photos/{id} one does the actual logic. Note: There are some obscure HTTP request verbs listed in https://www.w3.org/Protocols/HTTP/Methods.html that we don’t use, such as CHECKIN, LINK, and TEXTSEARCH. These are rarely recognized in HTTP request and server libraries, so they may just add an additional burden for us and others to implement. 2. Use kebab-case for paths, snake_case for parameters. Another common practice that we used here is to use kebab-case for REST paths and snake_case for parameters, even though that those are defined in the JSON format (which commonly written in camelCase instead). Yes, we do represent data model types (i.e. the kind of data being represented in objects, structs, and database tables) in PascalCase, but when it became part of the REST request, we use the former ones. You can learn more about the differences between these four naming conventions in the FreeCodeCamp. The reason why we used such conventions is to tolerate case-sensitivity, so user do not have to use certain uppercase letters to refer to the right data model. Additionally, web services conventionally used the snake_case for request parameters, so we leave the convention as-is for compatibility purposes. 3. Every response data should correspond closely to the enquired model. Well, we said we’re grouping things based on its model, right? So there has to be a standard way to represent the model and its items for each model-related responses. And that’s what we actually did: always map every model across database, source codes, and input/output serialization. In database, this means the table columns. In the source code, this is most likely to be objects (as in OOP) or structs as a fallback. In data serialization, we can use common serialization objects including JSON and YAML. We still do prefer JSON for REST API responses. For example, creating a new item under the model should give a HTTP response containing the new model, instead of simply signalling that “the insertion is complete” or just the item IDs. Similarly, when updating an item or two, the response should include the updated model items. There might be some exceptions for this, such as when doing batch processing, we could reduce the unnecessary response data load by signifying the updated item IDs, including which one were unchanged or faulty. In his own thesis, Reinhart listed his data type mapping across MySQL, MariaDB, Dart, PHP to ensure that the app’s entity models are properly represented from the database to the backend and frontend. 4. Our standard REST response. { "status": "OK", "data": /* ... */ "warning": /* ... */ } { "status": "KO", "error": /* ... */ "data": /* ... */ } Our standard response is always written in JSON unless a different format is required, e.g. returning an Atom/RSS feed in XML. This response is heavily inspired by the simplistic DuckDNS API and other REST API designs. We commonly fill in the error parameter with error codes, which may vary from system to system. Some of the common ones include {{MODEL}}_NOT_FOUND accompanied with the HTTP 404 status code and perhaps some additional diagnostic data located under the data paraeter. But some systems which require further debugging may return the error message as-is from the related software libraries on that error parameter. 5. Do not afraid of using HTTP response codes. HTTP 200 { "statusCode": 404, "data": "Blog Post not found." } The enterprise developer who made this should go to the hell! Source: https://twitter.com/goenning/status/1782330200958615637 Don’t worry, angry developers. We are still using HTTP status codes responsibly! 6. Now, what if we really need an endpoint that does not really fit into the above conventions? We have an internal term for it: import/export endpoints. They are endpoints which processes a standard model representation from or to the non-standard ones, such as importing items from CSV, or outputting a list of posts in Atom/RSS format. These endpoints do not follow some of our path conventions, but still need to contained inside a model path, such as /posts/feed and /products/import. The expected input and output data formats can deviate from the standard ones, too. Some of our systems also have to deal with other REST API standards, such as utilizing the /.well-known/ path for things related to digital identity and website verification. Many also respect the classic /ping endpoint, which expects to return a plaintext response of pong, to check whether the server is still active. And lastly, we also have a dedicated endpoint group, name /test. Since our model names are plural, we do not really care if the name conflicts with the model Test, since the model will eventually be represented as /tests/. These endpoints are meant for utilities to help developers integrate to our systems, such as /test/access-token to check whether an access token is still valid, and /v4/test/ping (alongside /ping) to check whether the service supports the REST API Version 4 schema.



Reinhart Previano Koentjoro
Reinhart Previano Koentjoro
Citra Manggala Dirgantara
Citra Manggala Dirgantara

A Reinhart company

Products

Company