<?xml version="1.0" encoding="UTF-8"?><rss version="2.0" xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:atom="http://www.w3.org/2005/Atom"><channel><title>Bagus Merta</title><description>software engineer from Indonesia who&apos;s passionate about Mobile and Front-end development</description><link>https://bagusmerta.com/</link><atom:link href="https://bagusmerta.com/rss.xml" rel="self" type="application/rss+xml"/><language>en-us</language><item><title>Translating Style Guides into Code</title><link>https://bagusmerta.com/blog/learning-design-and-styles-guides/</link><guid isPermaLink="true">https://bagusmerta.com/blog/learning-design-and-styles-guides/</guid><description>A learning experience in translating design principles into code</description><pubDate>Thu, 26 Sep 2024 00:00:00 GMT</pubDate><content:encoded>&lt;p&gt;As I began my software engineering career, I was captivated by the visual aspects of applications—whether it was a web applications, or mobile apps.
Throughout my journey, I’ve recently realized that as applications scale and grow, building user interfaces becomes more challenging, especially when more developers are involved.
This led me to dive deeper into studying reusable components, including design system and style guides, which form the foundation of our UI.&lt;/p&gt;
&lt;p&gt;In this post, I’ll share my learning experience from implementing a design system in my personal website.
The reason behind this post is I’ve developed and iterated on it numerous times, but I often found myself changing the entire theme and components, which led to inconsistency and a lack of cohesion across the site.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;P.S. This is also my first experience with web development, so there are probably quite a few mistakes along the way—feel free to point them out, I’d really appreciate it!&lt;/p&gt;
&lt;/blockquote&gt;
&lt;h2&gt;Three things you need&lt;/h2&gt;
&lt;p&gt;There are three key elements needed to develop a UI for an app, based on &lt;a href=&quot;https://leerob.io/blog/style-guides-component-libraries-design-systems&quot;&gt;Leerob&lt;/a&gt; post.&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;&lt;strong&gt;Style guides&lt;/strong&gt; : A set of rules that we follow, including constants like hex colors, padding sizes, fonts, and typefaces that represent the brand. This ensures components are built consistently. If we make changes, they stay within these guidelines, reducing the risk of breaking the design.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Design system&lt;/strong&gt; : The implementation of the style guides. For example, when creating a button, it must adhere to the style guide’s rules (e.g., correct fonts and colors). This approach makes components more robust and easier to maintain, even with multiple developers working on them. It also encourages building reusable, less duplicated code&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Component library&lt;/strong&gt; : It combines everything mentioned above—style guides and component libraries—into one complete system, along with detailed documentation and principles to ensure everything stays consistent. It’s like a blueprint that guides the design and development of your app.&lt;/li&gt;
&lt;/ol&gt;
&lt;h2&gt;Define design principles and our design token as a style guides&lt;/h2&gt;
&lt;p&gt;To begin, we need to define design principles and a style guide. This time, I’ve adopted principles inspired by &lt;a href=&quot;https://m3.material.io&quot;&gt;Material Design&lt;/a&gt; and &lt;a href=&quot;https://developer.apple.com/design/human-interface-guidelines/&quot;&gt;Apple HIG&lt;/a&gt;, with a bit of my own twist.
The focus is on Scalability, Clarity, Efficiency, and Simplicity.&lt;/p&gt;
&lt;h3&gt;Scalability&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;Purpose&lt;/strong&gt; : Design systems should be able to grow as the product or team evolves.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;How&lt;/strong&gt; : Create flexible components that can handle multiple use cases (e.g., button variations, responsive grids). Ensure new elements can be added without breaking existing styles.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Example&lt;/strong&gt; : A grid system that adapts to different screen sizes, or a button that supports various sizes and states (hover, disabled, etc.).&lt;/li&gt;
&lt;/ul&gt;
&lt;h3&gt;Clarity&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;Purpose&lt;/strong&gt; : Prioritize readability and ease of understanding for users.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;How&lt;/strong&gt; : Use clear visual hierarchy (through typography, color, and spacing), legible fonts, and high-contrast color schemes to make important elements stand out.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Example&lt;/strong&gt; : Clear headings, consistent icon usage, and defined spacing between sections to guide users through the content.&lt;/li&gt;
&lt;/ul&gt;
&lt;h3&gt;Efficiency&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;Purpose&lt;/strong&gt; : Reduce complexity for both users and developers.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;How&lt;/strong&gt; : Create a streamlined workflow for the design and development process. Make sure that components are easy to use and adapt to various situations without too much customization.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Example&lt;/strong&gt; : Predefined color and spacing tokens that developers can easily apply without guessing or writing extra CSS.&lt;/li&gt;
&lt;/ul&gt;
&lt;h3&gt;Simplicity&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;Purpose&lt;/strong&gt; : Keep designs straightforward to minimize cognitive load on users.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;How&lt;/strong&gt; : Avoid unnecessary elements, reduce visual clutter, and use intuitive patterns.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Example&lt;/strong&gt; : Minimalistic interface with clear call-to-action buttons, rather than overly decorative styles.&lt;/li&gt;
&lt;/ul&gt;
&lt;h2&gt;Creating design tokens&lt;/h2&gt;
&lt;p&gt;Design tokens represent a shared language for design attributes, allowing them to be written in code. Typically, we convert designs created by the design team into hardcoded values to maintain consistent and scalable UI components&lt;/p&gt;
&lt;p&gt;This includes things like: Colors (text, backgrounds, borders), Fonts, Typography sizes, Spacing values, Shadows&lt;/p&gt;
&lt;p&gt;For example, here are the hardcoded values for colors used in my components:&lt;/p&gt;
&lt;pre&gt;&lt;code&gt;@layer base {
    :root {
        --background: 222.2 84% 4.9%;
        --foreground: 210 40% 98%;
        --popover: 222.2 84% 4.9%;
        --popover-foreground: 210 40% 98%;
        --primary: 210 40% 98%;
        --primary-foreground: 222.2 47.4% 11.2%;
        --secondary: 217 91% 59%;
        --destructive: 0 62.8% 30.6%;
        --destructive-foreground: 210 40% 98%;
        --border: 217.2 32.6% 17.5%;
        --radius: 0.5rem;
        --card: rgba(255, 255, 255, 0.05);
        --card-hover: rgba(255, 255, 255, 0.1);
        --card-hover-border: rgba(255, 255, 255, 0.26);
      }
      ...
  }  
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;Next, in my &lt;code&gt;tailwind.config.mjs&lt;/code&gt;, I define these tokens so we can use them in Tailwind classes:&lt;/p&gt;
&lt;pre&gt;&lt;code&gt;export default {
	...
	theme: {
		extend: {
			fontFamily: {
				primary: [&apos;AlbertSans&apos;, ...fontFamily.sans],
				display: [&apos;PlayfairBold&apos;, ...fontFamily.sans],
				code: [&apos;DMMono&apos;, ...fontFamily.sans],
			  },
			  borderRadius: {
				lg: &apos;var(--radius)&apos;,
				md: &apos;calc(var(--radius) - 2px)&apos;,
				sm: &apos;calc(var(--radius) - 4px)&apos;,
			  },
			  colors: {
				background: &apos;hsl(var(--background))&apos;,
        		foreground: &apos;hsl(var(--foreground))&apos;,
				primary: {
					DEFAULT: &apos;hsl(var(--primary))&apos;,
					foreground: &apos;hsl(var(--primary-foreground))&apos;,
				},
				secondary: {
					DEFAULT: &apos;hsl(var(--secondary))&apos;,
					foreground: &apos;hsl(var(--secondary-foreground))&apos;,
				},
				destructive: {
					DEFAULT: &apos;hsl(var(--destructive))&apos;,
					foreground: &apos;hsl(var(--destructive-foreground))&apos;,
				},
				border: &apos;hsl(var(--border))&apos;,
			  },
			  ...
		},
	},
    ...
}
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;We also need to define the icon set we&apos;re using. For this website, I’m using open-source icons like simple-icons. Here&apos;s how I include them using Icon tag in &lt;a href=&quot;https://astro.build/&quot;&gt;Astro&lt;/a&gt;&lt;/p&gt;
&lt;pre&gt;&lt;code&gt;---
const icon = &apos;simple-icons:github&apos;;
---
&amp;lt;Icon class=&apos;text-2xl text-gray-400&apos; name={icon} /&amp;gt;
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;Make sure to consistently utilize icons from the same set to maintain visual uniformity throughout the app. I use &lt;a href=&quot;https://iconify.design/&quot;&gt;Iconify&lt;/a&gt; to find the exact icons that fit my needs.&lt;/p&gt;
&lt;h2&gt;Creating component library&lt;/h2&gt;
&lt;p&gt;After defining our style guides, it’s time to translate those guides into code. Based on the design tokens we&apos;ve already created, we&apos;ll now build components according to the design principles we agreed upon.&lt;/p&gt;
&lt;p&gt;For the button component, I decided to create two separate variations, with the primary button also having its own glowing variant.&lt;/p&gt;
&lt;pre&gt;&lt;code&gt;&amp;lt;PrimaryButton href=&quot;&quot; text=&quot;Glowing&quot; glowing={true} /&amp;gt;
&amp;lt;PrimaryButton href=&quot;&quot; text=&quot;Primary&quot; /&amp;gt;
&amp;lt;SecondaryButton href=&quot;&quot; text=&quot;Secondary&quot; /&amp;gt;
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;Here’s how they look.
&lt;/p&gt;
&lt;p&gt;Another example is the card component. I decided to create separate components for different types of cards since they serve different purposes. However, they all follow the same design principles we agreed upon. Below is my blog card, which emphasizes the importance of visual hierarchy.&lt;/p&gt;
&lt;pre&gt;&lt;code&gt;---
import type { BlogEntry } from &quot;utils/content&quot;;
import { formatDate } from &quot;utils/time&quot;;
import { getBlogPathName } from &quot;utils/url&quot;;
import { Icon } from &quot;astro-icon/components&quot;
import { Image } from &quot;astro:assets&quot;;
export type Props = BlogEntry;

const props = Astro.props;
---
&amp;lt;li class:list={[
  &apos;p-2 w-full rounded-lg border border-gray-900&apos;,
  &apos;bg-gradient-to-br from-[var(--card)]&apos;,
  &apos;scale-500 hover:scale-[1.02] active:scale-[0.97] motion-safe:transform-gpu&apos;,
  &apos;transition duration-500&apos;,
  &apos;motion-reduce:hover:scale-500&apos;,
  &apos;animate-shadow&apos;,
  &apos;hover:border-[var(--card-hover-border)] hover:shadow-[0_0_12px_var(--card-hover)]&apos;,
]}&amp;gt;
 ...
&amp;lt;/li&amp;gt;
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;As you can see, I used our --card value and its hover state, ensuring that each card is displayed consistently.&lt;/p&gt;
&lt;p&gt;Here&apos;s how it looks.
&lt;/p&gt;
&lt;h2&gt;Conclusion&lt;/h2&gt;
&lt;p&gt;That’s it! Now I have a solid foundation for my website. In the future, if we make changes or add new features, we’ll follow these style guides to ensure everything stays consistent with the theme.
Thanks for reading! I hope you found this helpful.&lt;/p&gt;
&lt;p&gt;References.&lt;/p&gt;
&lt;p&gt;&lt;a href=&quot;https://leerob.io/blog/style-guides-component-libraries-design-systems&quot;&gt;Leerob blog posts on design systems&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;&lt;a href=&quot;https://theodorusclarence.com/blog/btb-ui-fundamental&quot;&gt;Basic UI fundamental&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;&lt;a href=&quot;https://developer.apple.com/design/human-interface-guidelines/&quot;&gt;Apple HIG&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;&lt;a href=&quot;https://m3.material.io&quot;&gt;Material UI&lt;/a&gt;&lt;/p&gt;
</content:encoded></item><item><title>Well, you&apos;re just a man</title><link>https://bagusmerta.com/blog/well-youre-just-a-man/</link><guid isPermaLink="true">https://bagusmerta.com/blog/well-youre-just-a-man/</guid><description>Reminder for myself, maybe for you too</description><pubDate>Tue, 11 Jun 2024 00:00:00 GMT</pubDate><content:encoded>&lt;p&gt;Marcus Aurelius was the last of the Five Good Emperors who ruled the Roman Empire during a period known as the Pax Romana, or Roman Peace.&lt;/p&gt;
&lt;p&gt;I&apos;ve been a fan of Stoicism for years. Recently, I&apos;ve been listening to the audiobook of Marcus Aurelius&apos; Meditations. (Imagine listening to the diary of one of the most successful rulers in this modern age 🤣)&lt;/p&gt;
&lt;p&gt;Lately, life has been playing tricks on me, making me question the meaning of it all.&lt;/p&gt;
&lt;p&gt;Then I remembered a story about Marcus Aurelius.&lt;/p&gt;
&lt;p&gt;He was always respected by Roman citizens, with many even kneeling before him.&lt;/p&gt;
&lt;p&gt;And behind him, there was a slave who always stayed close.&lt;/p&gt;
&lt;p&gt;This slave only had one job — to remind him, whenever he felt on top of the world, whenever citizens worshipped him and knelt before him.&lt;/p&gt;
&lt;p&gt;The slave would whisper.&lt;/p&gt;
&lt;p&gt;&lt;a href=&quot;https://www.youtube.com/watch?v=SLP2RwDhOfg&quot;&gt;You&apos;re just a man&lt;/a&gt;&lt;/p&gt;
&lt;h3&gt;It humbles me.&lt;/h3&gt;
&lt;p&gt;Often, when I achieve something significant, I feel like I&apos;m the best or better than others.&lt;/p&gt;
&lt;p&gt;Then life reminds me that anything can be taken away as quickly as you can flip your hand.&lt;/p&gt;
&lt;h3&gt;Life always rotates.&lt;/h3&gt;
&lt;p&gt;There are times when we are up and times when we are down. We can&apos;t control the flow of the wind&lt;/p&gt;
&lt;p&gt;Yeah, you&apos;re just a man.&lt;/p&gt;
</content:encoded></item><item><title>Better way to write Commit Messages</title><link>https://bagusmerta.com/blog/better-way-to-write-git-commit-messages/</link><guid isPermaLink="true">https://bagusmerta.com/blog/better-way-to-write-git-commit-messages/</guid><description>Git conventional commit messages</description><pubDate>Thu, 30 May 2024 00:00:00 GMT</pubDate><content:encoded>&lt;p&gt;When working with a team, or even if you expect others to read your code, it&apos;s important to ensure that what you deliver is easy to understand. Often, when working alone on our repository, we might commit messages that seem appropriate at the moment. And that&apos;s fine. However, imagine needing to revisit a specific commit to find the exact cause of a bug or other important issues. If your commit message is clear, you won&apos;t need to spend so much time searching for it, right?&lt;/p&gt;
&lt;p&gt;This way of communicating through commit messages helps convey the intention behind the code changes. Everyone has their own style of writing commit messages; there&apos;s no one-size-fits-all solution. However, understanding what makes a good commit message can make you a better developer in the future.&lt;/p&gt;
&lt;h3&gt;Conventional Commit&lt;/h3&gt;
&lt;p&gt;The solution is to follow Conventional Commits. Conventional Commits provide a set of rules or guidelines to help us write semantic messages better.
Based on Conventional Commits, your message should be structured as follows:&lt;/p&gt;
&lt;pre&gt;&lt;code&gt;&amp;lt;type&amp;gt;[optional-scope]: &amp;lt;description&amp;gt;

# `type` is the type of change you made in your commit.
# `optional-scope` is the scope that your changes affect.
# `description` describes what was done.
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;If you have more to say:&lt;/p&gt;
&lt;pre&gt;&lt;code&gt;&amp;lt;type&amp;gt;[optional-scope]: &amp;lt;description&amp;gt;
[optional-body]
[optional-footer]
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;For example:&lt;/p&gt;
&lt;pre&gt;&lt;code&gt;feat(shop): add product card
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;A longer example:&lt;/p&gt;
&lt;pre&gt;&lt;code&gt;feat(payment): notify user upon successful purchase
Implement functionality to send a push notification to users when a product is successfully purchased. 
Refs: #123
&lt;/code&gt;&lt;/pre&gt;
&lt;h3&gt;Types&lt;/h3&gt;
&lt;p&gt;There are various types to differentiate the changes you make in your code:&lt;/p&gt;
&lt;pre&gt;&lt;code&gt;- feat → Changes related to adding or removing a feature.

- fix → Bug fixes (state the issue that you solved).

- docs → Documentation updates (e.g., README.md).

- style → Code style updates that don&apos;t change logic (e.g., optimizing imports, fixing whitespace).

- chore → Dependency management (e.g., installing or updating dependencies).

- refactor → Code changes that don&apos;t alter the external behavior but improve the internal structure.

- ci → Changes to CI configuration or scripts.

- test → Adding or updating tests.

- revert → Reverting a previous commit.

# Codemagic is an example of a CI/CD tool; you could replace it with your preferred tool.
- codemagic → Blank commit to trigger deployment (e.g., `codemagic: trigger deployment`).
&lt;/code&gt;&lt;/pre&gt;
&lt;h3&gt;Closing&lt;/h3&gt;
&lt;p&gt;What&apos;s important here is how you write the description.
Make sure you fully explain what is being done. Use imperative and present tense. Also, don&apos;t use capitals at the beginning of the sentence and don&apos;t add a full stop (.) at the end.&lt;/p&gt;
&lt;p&gt;References.
&lt;a href=&quot;https://www.conventionalcommits.org/en/v1.0.0/&quot;&gt;Conventional Commit Message&lt;/a&gt;&lt;/p&gt;
</content:encoded></item><item><title>Flutter pre-commit linter hooks</title><link>https://bagusmerta.com/blog/flutter-pre-commit-linter-hooks/</link><guid isPermaLink="true">https://bagusmerta.com/blog/flutter-pre-commit-linter-hooks/</guid><description>Use this to make your code look cleaner and more organized!</description><pubDate>Tue, 12 Mar 2024 00:00:00 GMT</pubDate><content:encoded>&lt;p&gt;working in a team can be quite challenging, especially when you&apos;re part of a startup engaged in fast-paced development, where there&apos;s a good chance of writing not-so-great code in such a rush.
But if we ignore it, we&apos;re just storing up problems for later. It will become a technical debt that going to slow down the development of our team,  and might even cause bugs and other headaches.&lt;/p&gt;
&lt;p&gt;One way to tackle this problem is to set a pre-commit hooks on our Repository. Luckily &lt;code&gt;Flutter.dev&lt;/code&gt; comes up with the official &lt;code&gt;flutter_lints&lt;/code&gt; package that contains a recommended set of lints for Flutter apps to leverage good coding practices.
This package is actually built on top of the Dart analyzer, which statically checks Dart code. So alternatively, we can analyze our code manually using the &lt;code&gt;flutter analyze&lt;/code&gt; command.
But that means we have to manually write the command every time we make changes, right? Rest assured, in this blog, I will show you a way to make it easier.&lt;/p&gt;
&lt;h3&gt;Pre-requisites&lt;/h3&gt;
&lt;ol&gt;
&lt;li&gt;You&apos;ll need a Flutter project with the latest versions of Flutter and Dart&lt;/li&gt;
&lt;li&gt;Make sure you have &lt;code&gt;pip&lt;/code&gt; installed if you&apos;re using windows otherwise you can use &lt;code&gt;brew&lt;/code&gt;&lt;/li&gt;
&lt;/ol&gt;
&lt;h3&gt;Installation&lt;/h3&gt;
&lt;p&gt;If you haven&apos;t already installed pre-commit, you can do so by following the instructions on the Pre-commit website. For most users, installing via Homebrew or pip is recommended.&lt;/p&gt;
&lt;pre&gt;&lt;code&gt;brew install pre-commit  # For macOS
# or
pip install pre-commit  # For other platforms
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;After that, you can initialize the pre-commit hooks inside your repository by creating &lt;code&gt;.pre-commit-config.yaml&lt;/code&gt; at the root of your project. This file specifies the hooks that should be run and any additional parameters needed for the linting process.
This will enforce code quality standards before each commit is made to our repository. Below is an example of my pre-commit config file, which will handle formatting and analyzing in our code.&lt;/p&gt;
&lt;pre&gt;&lt;code&gt;repos:
  - repo: local   # Specifies that the repository is local (not remote).
    hooks:
      - id: flutter-format
        name: Flutter Format
        entry: dart format .   # Command to execute for formatting Dart files.
        language: system     # Specifies the language environment for executing the hook.
        types: [dart]       # Specifies the file types to which this hook applies.
        pass_filenames: false   # Indicates whether filenames should be passed to the hook
      - id: flutter-analyze
        name: Flutter Analyze
        entry: flutter analyze  # Command to execute for analyzing Flutter code.
        language: system  
        types: [dart]
        pass_filenames: false
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;Then, add the &lt;code&gt;analysis_options.yaml&lt;/code&gt; to your root project and customize it for your own benefit.
This file is used to configure static analysis settings for Dart code, allowing you to specify various rules and settings that the Dart analyzer should follow when analyzing your codebase.&lt;/p&gt;
&lt;pre&gt;&lt;code&gt;include: package:flutter_lints/flutter.yaml

# This section specifies the linting rules 
linter:
  rules:
    # Define your custom rules here
    avoid_empty_else: true
    avoid_print: true
    avoid_relative_lib_imports: true
    avoid_returning_null_for_void: true
    avoid_unused_constructor_parameters: true
    avoid_void_async: true
    await_only_futures: true
    camel_case_types: true
    constant_identifier_names: true
    curly_braces_in_flow_control_structures: true
    file_names: true
    no_logic_in_create_state: true
    non_constant_identifier_names: false
    prefer_const_constructors: true
    prefer_const_literals_to_create_immutables: true
    prefer_final_fields: true
    unnecessary_null_checks: true
    unnecessary_this: true
    use_key_in_widget_constructors: true

# This section specifies the analyzer settings
analyzer:
  exclude: # Exclude certain files and directories from analysis.
    - lib/generated/**  
    - test/**           
    - &quot;**/*.g.dart&quot;     
    - &quot;**/*.freezed.dart&quot; 
  errors: # Specify how to handle certain types of analyzer errors.
    annotate_overrides: ignore
    avoid_print: ignore
    avoid_unnecessary_containers: ignore
    avoid_void_async: ignore
    camel_case_types: ignore
    constant_identifier_names: ignore
    dead_null_aware_expression: ignore
&lt;/code&gt;&lt;/pre&gt;
&lt;blockquote&gt;
&lt;p&gt;You can see the whole example of &lt;code&gt;analysis_options.yaml&lt;/code&gt; from the official Flutter project repository itself.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;h3&gt;Trigger the pre-commit linter hooks&lt;/h3&gt;
&lt;p&gt;Now that everything is set up, try making changes to your Flutter project, especially inside the &lt;code&gt;lib&lt;/code&gt; directory, and then commit your changes.&lt;/p&gt;
&lt;pre&gt;&lt;code&gt;  git add .
  git commit -m &quot;test precommit linter&quot;
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;Then, let the pre-commit linter work. It will give a green label if our commit is successful, as shown in the picture below. If not, the linter
will show you the code that needs to be changed based on the rules set in the &lt;code&gt;analysis_options.yaml&lt;/code&gt; file. After that, we need to re-commit our changes.
&lt;/p&gt;
&lt;h3&gt;Conclusion&lt;/h3&gt;
&lt;p&gt;Setting up pre-commit hooks can be a real game-changer for your team.
It&apos;s like having a helpful assistant that keeps your code clean and your development process smooth, even in the midst of fast-paced development.
Thanks for reading, happy coding :)&lt;/p&gt;
</content:encoded></item><item><title>Optimize Your Mobile Development Workflow with CodeMagic&apos;s</title><link>https://bagusmerta.com/blog/optimize-your-mobile-development-workflow-with-codemagic/</link><guid isPermaLink="true">https://bagusmerta.com/blog/optimize-your-mobile-development-workflow-with-codemagic/</guid><description>CI/CD tool for your mobile development</description><pubDate>Sat, 13 Jan 2024 00:00:00 GMT</pubDate><content:encoded>&lt;p&gt;Building mobile apps is super exciting, but it can also can be a challenge. Have you ever experienced the frustration of building a mobile app on your machine, only to face roadblocks when collaborating with team members?
In this blog, I&apos;ll introduce a solution which automating your mobile app builds with CodeMagic.&lt;/p&gt;
&lt;p&gt;With CodeMagic, you can streamline your development workflow and ensure consistent and reliable builds, regardless of your team&apos;s diverse environments. By automating the build process, you can avoid compatibility issues and focus on developing features that matter.&lt;/p&gt;
&lt;p&gt;Additionally, I&apos;ll show you how to integrate your workflow into Slack or Discord so that you can receive notifications every time a build is completed.&lt;/p&gt;
&lt;p&gt;CodeMagic offers a lot of features to make your CI/CD process easier, especially for mobile development. Initially, it only supported Flutter, but now you can add Android, iOS, and React Native, with many advanced configurations and APIs. It also provides a free tier, so you should give it a try.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;while CodeMagic provides a lot of options, the free tier offers 500 minutes every month for using their M1 machine. So, use it wisely.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;h3&gt;Setting up a CodeMagic account &amp;amp; Github repository&lt;/h3&gt;
&lt;p&gt;The first step is to sign up for a CodeMagic account using your preferred repository host. In this blog, I&apos;ll be using Github since it&apos;s commonly used.
After signing up, head to the CodeMagic dashboard. Click on &quot;Add Application&quot; to create a new app. Choose the individual plan, then paste the link of your Github repository where you want to connect it with CodeMagic. Finally, click &quot;Finish: Add Application&quot; to complete the process.&lt;/p&gt;
&lt;p&gt;There are two options to enable the workflow, using a .yaml file and using the workflow editor on the CodeMagic dashboard. I personally prefer using the yaml approach because it helps me learn scripting as well.&lt;/p&gt;
&lt;p&gt;This is basically what your dashboard looks like after completing the repository addition.&lt;/p&gt;
&lt;p&gt;&lt;/p&gt;
&lt;p&gt;Before we dive into creating your &lt;code&gt;codemagic.yaml&lt;/code&gt; to initiate the workflow, we need to manually add the webhook URL of our CodeMagic app to our GitHub repository. Go to your application dashboard, and copy the webhook URL for your CodeMagic application.&lt;/p&gt;
&lt;p&gt;&lt;/p&gt;
&lt;p&gt;And then go to your GitHub repository &amp;gt; Settings &amp;gt; Webhooks and paste the CodeMagic webhook URL into your repository.&lt;/p&gt;
&lt;p&gt;&lt;/p&gt;
&lt;p&gt;And voila! your CodeMagic and Github are connected now.&lt;/p&gt;
&lt;h3&gt;Creating your &lt;code&gt;codemagic.yaml&lt;/code&gt;&lt;/h3&gt;
&lt;p&gt;Alright, let&apos;s start the coding session.  To really get how things work, we&apos;ll begin with the simplest setup.
Also, it&apos;s good to understand the basics before moving on to more advanced configurations.&lt;/p&gt;
&lt;p&gt;First you need to define your workflow ID (with &apos;-&apos; to separate each word) and also the name and maximum build duration of your app.&lt;/p&gt;
&lt;pre&gt;&lt;code&gt;workflows:
  android-workflow-id:                    # your workflow ID
    name: &quot;Android ToDo&apos;s App Workflow&quot; 
    max_build_duration: 120               # max duration of your build
    instance_type: mac_mini_m1            # remote machine to run your workflow
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;Next, we have the &lt;code&gt;environment&lt;/code&gt; property, which is commonly used to specify your project&apos;s settings for building.
For example, you can specify the versions of Flutter or Java used in your project.&lt;/p&gt;
&lt;pre&gt;&lt;code&gt;workflows:
  android-workflow-id:
    ...
        environment:  # env scope for your build
            flutter: 3.0.5
            java: 17
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;This one is really important - &lt;code&gt;triggering&lt;/code&gt; is the property that makes your build run based on actions or events in your GitHub repository.&lt;/p&gt;
&lt;p&gt;There are 4 build triggers, but I&apos;ll write just 3 most important (at least for me) :&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;push&lt;/strong&gt; : starts every time you commit code to any of the tracked branches.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;pull_request&lt;/strong&gt; : starts when a pull request is opened or updated to verify the resulting merge commit.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;tag&lt;/strong&gt; : automatically builds the tagged commit whenever you create a tag for this app.&lt;/li&gt;
&lt;/ul&gt;
&lt;pre&gt;&lt;code&gt;workflows: 
  ...
    triggering:
          events:
            - push  # trigger on push events
          branch_patterns:
            - pattern: &quot;*&quot; # * indicates any branch pattern (main, dev etc)
              include: true
              source: true
&lt;/code&gt;&lt;/pre&gt;
&lt;blockquote&gt;
&lt;p&gt;When setting up triggers for pull requests, you can choose whether each branch pattern matches the source or target branch of the pull request.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;you can read more about the &lt;code&gt;triggering&lt;/code&gt; property on their docs&lt;/p&gt;
&lt;p&gt;Next up is the &lt;code&gt;scripts&lt;/code&gt; property, where you put the scripts needed to run your build. Make sure the order of your scripts is correct because they are executed from top to bottom.&lt;/p&gt;
&lt;p&gt;Also, it&apos;s helpful to have a basic understanding of how to use Linux commands. This knowledge will allow you to make the most of its features, especially for debugging purposes.&lt;/p&gt;
&lt;pre&gt;&lt;code&gt;workflows:
  ...
    scripts:
    - name: Set up local.properties     
      script: |
        echo &quot;flutter.sdk=$HOME/programs/flutter&quot; &amp;gt; &quot;$CM_BUILD_DIR/android/local.properties&quot;
    - name: Get Flutter packages
      script: |
        flutter packages pub get
    - name: Build Debug App with Flutter
      script: |
        flutter build apk --debug
    - name: Show Build apk Folder  # tips. add this command to see the content of your artifact
      script: |
        ls build/app/outputs/flutter-apk
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;Lastly, we can specify the &lt;code&gt;artifact&lt;/code&gt;, which stores our build results, and the publishing property, which contains options for where you want to publish your artifact.&lt;/p&gt;
&lt;pre&gt;&lt;code&gt;workflows: 
  ...
    scripts:
      ...
      ...
    artifacts:                       
      - build/app/outputs/flutter-apk/*.apk  # specify path to store your artifact 
    publishing:
      email:
        recipients:
          - example@gmail.com  # email recipient in case you want to see the reports
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;This is the full code of your &lt;code&gt;codemagic.yaml&lt;/code&gt; to start the workflow.&lt;/p&gt;
&lt;pre&gt;&lt;code&gt;workflows:
  android-workflow-id:
    name: &quot;Android ToDo&apos;s App Workflow&quot;
    max_build_duration: 120
    instance_type: mac_mini_m1
    environment:
      flutter: stable
    cache: # tips. add cache mechanism to fasten your build process
      cache_paths:
        - ~/.pub-cache
    triggering:
      events:
        - push
      branch_patterns:
        - pattern: &quot;*&quot;
          include: true
          source: true
    scripts:
      - name: Set up local.properties
        script: |
          echo &quot;flutter.sdk=$HOME/programs/flutter&quot; &amp;gt; &quot;$CM_BUILD_DIR/android/local.properties&quot;
      - name: Get Flutter packages
        script: |
          flutter packages pub get
      - name: Build Debug App with Flutter
        script: |
          flutter build apk --debug
      - name: Show Build apk Folder
        script: |
          ls build/app/outputs/flutter-apk
    artifacts:
      - build/app/outputs/flutter-apk/*.apk
    publishing:
      email:
        recipients:
          - example@gmail.com
&lt;/code&gt;&lt;/pre&gt;
&lt;h3&gt;Start the builds&lt;/h3&gt;
&lt;p&gt;To kick off your CodeMagic workflow, you have two options. You can either use the CodeMagic dashboard to manually start your build, or you can set up triggering events based on your codemagic.yaml file. For instance, you might want to start the build every time you push new changes to your repository.&lt;/p&gt;
&lt;p&gt;If everything goes smoothly, you&apos;ll be able to see the artifact in the build overview of your app.&lt;/p&gt;
&lt;p&gt;&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;You can also debug your build process using SSH or VNC access. This can be very helpful if you need to troubleshoot any issues on your remote machine.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;h3&gt;Integration with Discord&lt;/h3&gt;
&lt;p&gt;Lets start diving into the fun part.
First, you need to obtain your Discord webhooks from your channel where you want to receive notifications. Then, add the webhook URL to the environment section in your CodeMagic app.&lt;/p&gt;
&lt;p&gt;You can access your variables in your workflow code using the &lt;code&gt;$&lt;/code&gt; symbol in front of them (like &lt;code&gt;$DISCORD_WEBHOOK_URL&lt;/code&gt;). Also, you need to specify the variable group that you created inside the &lt;code&gt;environment&lt;/code&gt; property.&lt;/p&gt;
&lt;p&gt;&lt;/p&gt;
&lt;p&gt;To connect with Discord, you can include this command within the publishing section.&lt;/p&gt;
&lt;pre&gt;&lt;code&gt;workflows:
  ...
    environment:
      groups:
        - discord_credentials # variable group that stores discord webhook
    ...
  
    publishing:
      ...

      scripts:
        - name: Discord notification # use the webhook URL at the end of the scripts
          script: |
            set -ex

            # Extract the App Link from CM_ARTIFACT_LINKS
            APP_LINK=$(echo &quot;$CM_ARTIFACT_LINKS&quot; | jq -r &apos;.[] | select(.name == &quot;app-debug.apk&quot;) | .url&apos;)

            # Get the first 7 digits of the commit number
            COMMIT=$(echo &quot;${CM_COMMIT}&quot; | sed &apos;s/^\(........\).*/\1/;q&apos;)

            # Get the commit message
            COMMIT_MESSAGE=$(git log --format=%B -n 1 $CM_COMMIT)

            # Get the commit author
            AUTHOR=$(git show -s --format=&apos;%ae&apos; $CM_COMMIT)

            # Publish the notification
            curl -H &quot;Content-Type: multipart/form-data&quot; \
              -F &quot;payload_json={
                \&quot;username\&quot;: \&quot;codemagic-bot\&quot;,
                \&quot;content\&quot;: 
                \&quot;**Commit:**   \`$COMMIT\`\\n**Commit message:** $COMMIT_MESSAGE\\n\\n**Branch:** $CM_BRANCH\\n
                **Author:** $AUTHOR\\n\\n**Artifacts:**\\n\\n**App Links:** $APP_LINK\\n\\n\&quot;}&quot; \
              $DISCORD_WEBHOOK_URL            
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;Make changes and try pushing them to your remote repository. If the build is successful, you&apos;ll receive a notification.&lt;/p&gt;
&lt;p&gt;&lt;/p&gt;
&lt;h3&gt;Conclusion&lt;/h3&gt;
&lt;p&gt;This tool comes with many benefits for your development – it speeds up development and resolves your build problems. It can also automate your testing, deployment, or publishing your app to PlayStore or AppStore, among many other features.&lt;/p&gt;
&lt;p&gt;Well, that&apos;s all for this blog. Pretty cool, right? Give it a try, and your future self and teammates will thank you.&lt;/p&gt;
&lt;p&gt;References.
&lt;a href=&quot;https://docs.codemagic.io/yaml-quick-start/building-a-flutter-app/&quot;&gt;Codemagic Official Docs&lt;/a&gt;&lt;/p&gt;
</content:encoded></item><item><title>Unpacking 2023</title><link>https://bagusmerta.com/blog/unpacking-2023/</link><guid isPermaLink="true">https://bagusmerta.com/blog/unpacking-2023/</guid><description>Lessons learned and hopes for tomorrow.</description><pubDate>Sun, 31 Dec 2023 00:00:00 GMT</pubDate><content:encoded>&lt;p&gt;2023 has been quite a journey, filled with ups and downs. I&apos;m putting together this blog to help me look back on what I&apos;ve been through, what I&apos;ve learned, and my hopes for the next year.&lt;/p&gt;
&lt;p&gt;It&apos;s like a friendly chat with myself, a little snapshot of lessons and dreams for the next 23 years.&lt;/p&gt;
&lt;p&gt;Lets Roll.&lt;/p&gt;
&lt;h3&gt;1. Take the initiative, don’t hesitate&lt;/h3&gt;
&lt;p&gt;If I&apos;ve learned anything impactful this year, it&apos;s the importance of taking initiative in almost every situation. I can provide a few examples:&lt;/p&gt;
&lt;p&gt;When I entered my final year and had to write a thesis, many college students faced challenges, especially when dealing with professors, whether it was finding a suitable time for discussions or getting their thesis drafts corrected. One thing that made it much easier for me was taking the initiative. I personally reached out to the professor, kept him informed about my progress, suggested meeting at his coffee shop for discussions, and took the lead in creating a group chat specifically for our professor. This initiative made it simpler for my friends to access information related to our professor&apos;s schedule. The key point is that it made me stand out more in front of my professor.&lt;/p&gt;
&lt;p&gt;I got multiple opportunities by reaching out first. I asked a senior engineer I know if there was a position that would be a good fit for me and requested a referral. I even reached out to the CEO of the company. Nowadays, you have various tools to make reaching out easier, such as LinkedIn, Twitter (X), email, etc. Of course, you also need to build trust and improve your online presence by creating projects or enhancing your profiles.&lt;/p&gt;
&lt;p&gt;I used to be afraid to reach out to someone, always fearing that the person I contacted would somehow be annoyed. But honestly, after all of this, it doesn&apos;t really matter as long as you maintain good etiquette and attitude. The worst thing you can receive is a rejection, so go get it!.&lt;/p&gt;
&lt;h3&gt;2. Always follow-up&lt;/h3&gt;
&lt;p&gt;I lost many opportunities because I hesitated to follow up. Whether applying for a job or acquiring a client, The mindset we should be focused on is &lt;em&gt;What exactly I can provide to them, addressing the challenges they&apos;re facing, without expecting an immediate reward&lt;/em&gt;.&lt;/p&gt;
&lt;p&gt;The person you&apos;re dealing with should discover that you excel in areas where they may struggle. How? By consistently following up. Send emails or messages with attachments of your work, do it at least once a day. Let them see your persistence and genuine interest in seizing opportunities. Along the way, you may encounter cold emails and rejections, but over time, you&apos;ll get used to it and develop a mindset of saying, &quot;Okay, good, let&apos;s move on to the next.”&lt;/p&gt;
&lt;h3&gt;3. Handling rejections&lt;/h3&gt;
&lt;p&gt;It&apos;s almost similar to the two points I mentioned above, but this one has a slightly different perspective. Rejections suck—everyone hates them.&lt;/p&gt;
&lt;p&gt;Throughout my life, I&apos;ve faced numerous rejections, to the extent that I started questioning my self-worth. Each rejection felt like a direct hit to my self-esteem, making me believe I was never good enough for anything. It was incredibly challenging to pick myself up and move forward.&lt;/p&gt;
&lt;p&gt;Now, instead of viewing rejections as attacks on my self-esteem, I prefer to see them as life lessons that help build my resilience. Often, the reasons behind rejection stem from external factors beyond our control, rather than our personal weaknesses.&lt;/p&gt;
&lt;p&gt;Most importantly, it teaches me to remain humble and be grateful for what I already have and have learned. It motivates me to deal with and overcome the difficulties that life brings.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;I plan to create an article about this specific topic, maybe next month—stay tuned! haha.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;h3&gt;4. Say goodbye to Your Routine&lt;/h3&gt;
&lt;p&gt;No lie, I&apos;m obsessed with self-development. So much so that I&apos;ve built a routine, like waking up in the morning, grabbing a coffee, working out, and so on. Let me give you a clearer example. I need that cup of coffee to kickstart my day, and if I skip it, I won&apos;t be productive, and my day feels suck. This goes for other things too, not sticking to these routines affects my ability to fully tap into my potential for the day.&lt;/p&gt;
&lt;p&gt;After enduring many bad days and battling procrastination, I realized that relying too heavily on routines can actually make us weaker. Insisting on having a coffee to get the job done is like making a statement about how the world should be when you have no control over it.&lt;/p&gt;
&lt;p&gt;Think about it. Initially, you need that morning coffee to feel better and get things done, but over time, you end up needing it just to feel normal. Eventually, the benefits that coffee once provided are gone.&lt;/p&gt;
&lt;p&gt;Believe it or not, there were humans, maybe a hundred years ago, who had none of these things and still got things done. It weakens me and makes me less resilient.&lt;/p&gt;
&lt;p&gt;The solution is to have no routine at all and just do things that need to get done, regardless of how you feel. I know, It&apos;s easier said than done, but I believe it makes me more resilient.&lt;/p&gt;
&lt;h3&gt;5. You’ll never be ready&lt;/h3&gt;
&lt;p&gt;This idea applies to anything in life. While it&apos;s good to have some basic knowledge before starting, it doesn&apos;t have to be perfect. Waiting is always tempting and often leads to procrastination. Whether it&apos;s starting something new or sharing your work, the urge to wait until you have more skills or feel completely ready is common. But when will that be?&lt;/p&gt;
&lt;p&gt;It&apos;s tricky, The real truth is, you&apos;ll never feel completely ready.&lt;/p&gt;
&lt;p&gt;After reading and watching a bunch of stuff, the best time to start is when you&apos;re unsure, especially when the path ahead isn&apos;t clear.&lt;/p&gt;
&lt;h3&gt;6. Less social media, more peace of minds&lt;/h3&gt;
&lt;p&gt;I&apos;ve cut down on social media almost every day. I only open it for important events that my close friends or my girlfriend are involved in, where I post or send messages to make myself and them feel acknowledged. It might sound strange, but I think it&apos;s almost impossible not to have social media in this modern age since everything is happening online. However, I believe it&apos;s crucial to set limits so that we don&apos;t become overly dependent or obsessed with it.&lt;/p&gt;
&lt;p&gt;Having face-to-face conversations with people has always been my preference over chatting on social media. Sometimes, I mindlessly scroll too, especially on tough days. However, I&apos;ve realized what happens and decided to log out or hide the apps on days when I need zero distractions.&lt;/p&gt;
&lt;h3&gt;7. A few good friend is enough&lt;/h3&gt;
&lt;p&gt;Well, I think I&apos;ve lost touch with many friends along the way, not because of any disagreement, but I&apos;ve realized everyone has their own stuff and needs to go in different directions. Sometimes, I discover I don&apos;t click with certain people, maybe because of their attitude, behavior, the environment, or it&apos;s just me. But I&apos;ve learned to be okay with it, even though it was tough.&lt;/p&gt;
&lt;p&gt;I have a group of friends and close pals who empower me to keep going. They inspire me, surpass me in certain aspects, and provide support. I believe that&apos;s sufficient.&lt;/p&gt;
&lt;h3&gt;8. Relationship, love&lt;/h3&gt;
&lt;p&gt;I&apos;ve learned a bunch about relationships this year, especially the ones with loved ones. I now get why looks don&apos;t matter much when you have someone who supports you, no matter what situation you&apos;re in, and I&apos;m really thankful for that. The important thing is talking openly. No matter what comes up, we need to trust each other, not set strict rules in the relationship, and support one another. I give advice when she needs it and agree with her perspective when it just feels right, even if it&apos;s actually wrong—haha.&lt;/p&gt;
&lt;p&gt;Just like any other connection and relationship, people need to be valued and respected. That&apos;s the fundamental thing I&apos;ve learned.&lt;/p&gt;
&lt;h3&gt;9. Health is your super-power&lt;/h3&gt;
&lt;p&gt;This year, I got sick too often, and it reached the worst stage – I had GERD from consistently delaying meals, and it felt terrible. I don&apos;t know why, but it always happened when there was an important event, be it a family reunion or just meeting friends at a coffee shop. I realized that if I want to stay on track, I need to maintain my health by leading a healthy life. I&apos;ve witnessed quite a lot – relatives with lots of money, yet every month they&apos;re dealing with health issues and hospital check-ups.&lt;/p&gt;
&lt;p&gt;Life is like a marathon, and at the end of the day, I simply want an okay life. I want my parents to retire, to assist friends and people dear to me, pay off bills, and handle other essential aspects of living. But if I&apos;m not in good health, how am I supposed to achieve that? Even if it takes 10 years, at least with good health, I can keep pursuing my dreams.&lt;/p&gt;
&lt;h3&gt;10. Learn, Practice, Repeat&lt;/h3&gt;
&lt;p&gt;Never stop learning. In the past, the fast-paced trends in Software Engineering made me feel burnout, but now I&apos;ve learned that, with technology growing rapidly, what you need are fundamental knowledge, patience, and a strong work ethic. I believe tools or frameworks are essentially the same, and you can leverage your understanding to learn other things. What I&apos;ve learned is to pick one thing (like learning React for web development), but ensure you understand JavaScript and HTML/CSS as well. Try to build a project—it doesn&apos;t need to be fancy, just enough to make the knowledge stick in your brain.&lt;/p&gt;
&lt;p&gt;If you&apos;re able to maintain a steady learning pace and be patient, when opportunities come, I believe we can at least handle the basics and work ourselves to the next step. I often feel the pressure to master something in one go, which is impossible (at least for me).&lt;/p&gt;
&lt;p&gt;In today&apos;s world, instant gratification affects us in almost every aspect. That&apos;s why learning to learn, being patient, and staying resilient is rare, even for myself. So, I&apos;m gonna keep on learning until it becomes a natural part of who I am.&lt;/p&gt;
&lt;p&gt;Well, that&apos;s it! It encompasses everything I&apos;ve learned. Of course, I could go on with a much longer list, but I believe that&apos;s all the things that have stuck in my brain.&lt;/p&gt;
&lt;h3&gt;Eight Things I&apos;m Going to Do&lt;/h3&gt;
&lt;p&gt;Now. lets write a list of things I’m going to do next year, The 2024. Lets get into it.&lt;/p&gt;
&lt;h4&gt;1. Hit the gym, regularly&lt;/h4&gt;
&lt;p&gt;It brings you good health and a bonus of looking good, so you won&apos;t have to worry about choosing clothes that suit you. I&apos;ve noticed many influencers with great bodies who just rock simple outfits. I aspire to be like that—haha.&lt;/p&gt;
&lt;h4&gt;2. Learn more instead trying to earn more&lt;/h4&gt;
&lt;p&gt;You&apos;re still young, a lot of stuff will happen in the future. What you need is experience and if you go for earning you will stop learning. Learn every skill along the way, not only stuff related to software engineering.&lt;/p&gt;
&lt;h4&gt;3. Practice English, writing and speaking&lt;/h4&gt;
&lt;p&gt;I need to improve because, right now, I still rely on ChatGPT to write this blog, lol. I also want to speak English fluently to open up more opportunities in the future. You can start by using DuoLingo, writing and reading English blogs, and watching English videos.&lt;/p&gt;
&lt;h4&gt;4. Create a YouTube Video on Your Expertise&lt;/h4&gt;
&lt;p&gt;You know, almost everything I&apos;ve learned is from video formats, mainly YouTube. So, I thought maybe I could contribute to the community by sharing something I know.&lt;/p&gt;
&lt;h4&gt;5. Write a blog post, at least once a month&lt;/h4&gt;
&lt;p&gt;I just want a space where I can chat with myself and, in the process, improve my English writing skills. Hehe.&lt;/p&gt;
&lt;h4&gt;6. Becomes better son, better brother, better partner and friends.&lt;/h4&gt;
&lt;p&gt;Literally becoming a better human. I&apos;ve made a lot of mistakes, probably upset people until today. That&apos;s why I need to be better for myself and learn to respect myself.&lt;/p&gt;
&lt;h4&gt;7. Invest in stock&lt;/h4&gt;
&lt;p&gt;Learn how to make your money works for you, just make sure to use specified Investment budget and learn the stock that you want to invest with.&lt;/p&gt;
&lt;h4&gt;8. Make a proper portfolio, blog site. (Using proper tech-stack and domain)&lt;/h4&gt;
&lt;p&gt;I want others to be able to subscribe and comment on my content so that I can receive feedback about my writing.&lt;/p&gt;
&lt;h3&gt;Closing&lt;/h3&gt;
&lt;p&gt;All in all, the purpose of this article really only for me to look back and laugh. And it took longer than I thought. Thanks for reaching this page. I hope you can get something out of it.&lt;/p&gt;
</content:encoded></item><item><title>Do it First</title><link>https://bagusmerta.com/blog/do-it-first/</link><guid isPermaLink="true">https://bagusmerta.com/blog/do-it-first/</guid><description>I gained something after watching a podcast featuring Chris and Goggins.</description><pubDate>Sat, 07 Oct 2023 00:00:00 GMT</pubDate><content:encoded>&lt;p&gt;So I randomly stumbled upon this new podcast with Chris William and David Goggins.
And guess what? It&apos;s like I&apos;ve got this instant insight into his whole deal.&lt;/p&gt;
&lt;p&gt;To simplify,
If there’s something that you’d like to do or some condition you’d like to be true, let it happen.&lt;/p&gt;
&lt;p&gt;Believe it’s going to happen.&lt;/p&gt;
&lt;p&gt;Write it down.&lt;/p&gt;
&lt;p&gt;Now, start chatting it up with yourself.&lt;/p&gt;
&lt;p&gt;I’ve got this.&lt;/p&gt;
&lt;p&gt;You can do it.&lt;/p&gt;
&lt;p&gt;The big thing here is taking action. The brain can be a bit of a slowpoke, so just get moving, literally.
Tell your body to go before your brain&apos;s even figured it out.&lt;/p&gt;
&lt;p&gt;Want to write a book? Easy, stare at a blank page for an hour each day until words start popping out.&lt;/p&gt;
&lt;p&gt;If you&apos;d like to run stare at your shoes for a few minutes until you start running.&lt;/p&gt;
&lt;p&gt;If you&apos;d like to write code, just open your favorite Editor (IDE) for a few moment.&lt;/p&gt;
&lt;h3&gt;That&apos;s Insane 🤣&lt;/h3&gt;
&lt;p&gt;Sure, there are limits to what you know, but sometimes you&apos;ve gotta trick that brain of yours into action.
Take a cue from David Goggins, put yourself out there, and let the rest catch up.&lt;/p&gt;
&lt;p&gt;Sometimes the things we tell ourselves or believe can sound a bit crazy.
But if you think about it, pretty much everyone who&apos;s achieved something cool has embraced a bit of madness along the way.&lt;/p&gt;
&lt;h3&gt;The point is the same&lt;/h3&gt;
&lt;p&gt;And you know what? It goes for a simple life too. Fly under the radar, lay low for a while, lay low forever and enjoy
the simplicity of existence.&lt;/p&gt;
&lt;p&gt;To close this post, I would like to share a quote by Alex Hormozi.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;The harder you work the more you realize what you used to think was hardwork,
is not even close to what you&apos;re capable of.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;That&apos;s it for this post. I hope it can be some kind of useful to anyone who reads it.
Feel free to always reach me out.&lt;/p&gt;
&lt;p&gt;—I&apos;d love to receive your thoughts on this piece!&lt;/p&gt;
&lt;p&gt;References.
&lt;a href=&quot;https://youtu.be/ngvOyccUzzY?si=KA-JWfYPwZ0m9SS_&quot;&gt;Chris William and David Goggins Podcast&lt;/a&gt;&lt;/p&gt;
</content:encoded></item></channel></rss>