# Grayhat Blog Tag: Software Engineering > Expanded public blog context for posts tagged Software Engineering. ## Page - [Software Engineering Tag](https://grayhat-company-blog.grayhatstudio.workers.dev/blog/tag/software-engineering) - [Software Engineering Tag LLM Context](https://grayhat-company-blog.grayhatstudio.workers.dev/blog/tag/software-engineering/llms.txt) - [Root LLM Context](https://grayhat-company-blog.grayhatstudio.workers.dev/blog/llms.txt) - [Root Full LLM Context](https://grayhat-company-blog.grayhatstudio.workers.dev/blog/llms-full.txt) - [Tag API](https://grayhat-company-blog.grayhatstudio.workers.dev/blog/api/public/v1/tags/software-engineering) ## Tag Details - Slug: `software-engineering` - Description: Not provided - Post count in current snapshot: 6 ## Current Posts - ["I can talk to machines"](https://grayhat-company-blog.grayhatstudio.workers.dev/blog/i-can-talk-to-machines) - Lessons from Saleem Koul’s journey through robotics, telecom, and engineering at scale. - [Full Stack Deployment: Setting Up CI/CD for Node.js Applications on AWS with Custom Domains](https://grayhat-company-blog.grayhatstudio.workers.dev/blog/full-stack-deployment-setting-up-ci-cd-for-node-js-applications-on-aws-with-custom-domains) - This comprehensive guide will walk you through establishing a professional CI/CD pipeline for Node.js applications on AWS EC2, complete with custom domain configuration. - [Pixels to Players: How Good Game Designs are Executed](https://grayhat-company-blog.grayhatstudio.workers.dev/blog/pixels-to-players-how-good-game-designs-are-executed) - Taking a game from an idea to reality is hard. How do you navigate through a sea of endless ideas and technologies, to deliver something... fun? - [Building a Unity Plugin in JavaScript](https://grayhat-company-blog.grayhatstudio.workers.dev/blog/building-a-unity-plugin-in-javascript) - Make your JS Library compatible with Unity. - [Reject Cloud, return to onprem](https://grayhat-company-blog.grayhatstudio.workers.dev/blog/reject-cloud-return-to-onprem) - Make the Cloud Overlords tremble in fear with your half-baked SSH and Wake-on-LAN powered virtual machine emulator. - [The Evolution of SecOps, DevOps, DevSecOps, GitOps, and Developer Experience](https://grayhat-company-blog.grayhatstudio.workers.dev/blog/the-evolution-of-secops-devops-devsecops-gitops-and-developer-experience) - In the fast-paced world of software development, staying ahead of the curve is essential. As build times shorten, Sprint cycles shorten, and remote culture rises, the management of the Software Development Lifecycle is rapidly being transferred from the hands of managers into the hands of developers themselves. Auditing by a manager is no longer a one-time thing; metrics of software quality like security, performance, code quality, and testing have been delegated to the developers themselves. T ## Child Route Content ### ["I can talk to machines"](https://grayhat-company-blog.grayhatstudio.workers.dev/blog/i-can-talk-to-machines) - Slug: `i-can-talk-to-machines` - Published: 2025-10-09T22:09:12.000+05:00 - Updated: 2025-11-04T23:26:44.000+05:00 - Reading time: 6 min - Tags: Events, Software Engineering, Company Culture - Authors: Saad Bazaz - Visibility: public We had an awesome session with Saleem Koul, senior Software Engineer who has worked for around 30 years with multiple Big Tech companies including Motorola, Nokia and more (Intel, Qualcomm). ## TLDR; Based on his extensive career at industry giants like Nokia and Motorola, Mr. Saleem Koul emphasized that large, successful companies like Nokia operate on core principles of **Focus, Innovation, and Quality**. He illustrated that the best engineers distinguish themselves by proactively seeking solutions and automating processes, not just completing assigned tasks. True innovation, he taught, comes from a personal drive to improve systems and make the work of your entire team easier and more efficient, often by identifying manual bottlenecks and creating automated solutions that enhance speed, accuracy, and scalability. Ultimately, he championed the mindset of owning a problem, finding the optimal solution, and consistently striving to elevate both the product and the people around you. Saleem Koul’s career spans robotics, embedded systems, telecom infrastructure, and 5G networks. Across these domains, his approach has been consistent: focus on solving real problems, automate wherever possible, and hold the line on engineering quality. He’s seen how large companies like Nokia operate at scale, and he’s distilled clear lessons on what it takes to become an exceptional engineer inside complex organizations. ## Early Foundations Saleem’s path began at the **Pakistan Atomic Energy Commission**, in a robotics lab experimenting with early AI methods. Long before machine learning became mainstream, he worked with **single-layer perceptrons*** and **genetic algorithm**...** ***back in the late 80s and early 90s, when AI was in its early stages. He later moved to the **University of Texas at Arlington**, where he pursued **Digital Signal and Image Processing**, **Computer Vision**, and **Medical Imaging**. His research combined **MRI’s structural data with PET’s functional imaging**, improving the clarity and diagnostic utility of scans. He also worked on early UAV stability problems, applying control theory to keep aircraft stable — well before drones were commercialized. *## Entering Telecom Saleem joined **Nortel** during the UMTS rollout, then moved to **Motorola** and later **Nokia** (via Motorola’s acquisition). His core work was in **embedded systems**, developing and testing **vocoders**, signal processing components, and low-level code for **PowerPC architectures**. At Nokia, he observed that the company’s scale and resilience rested on three clear operational principles: **Focus, Innovation, and Quality**. - **Focus** meant that projects were broken into essential, well-defined components. Distractions were minimized. - **Innovation** wasn’t about brainstorming sessions; it was about finding better ways to do the work already at hand. - **Quality** was non-negotiable — systems shipped only when they met rigorous internal standards, because failure at network scale was not an option. Saleem often emphasizes that **a great engineer isn’t the one who merely finishes the task, but the one who finds the most effective way to do it**, even if that means redesigning the approach. ## Automating the Hard Work One of his most impactful contributions was in **network testing automation**. Traditionally, telecom teams performed manual drive tests: engineers would drive through test areas at night, measuring **signal strength**, **handover performance**, and **call reliability**. This process was slow, error-prone, and heavily dependent on human coordination. Saleem developed a fully automated system — later nicknamed the **Uber Driver** project. Using **Snapdragon devices**, **Qualcomm QXDM**, GPS triggers, and custom scripts, his solution automated the entire process: data collection, post-processing, visualization, and reporting. By morning, the system generated **Google Earth maps** and **presentation decks** without human intervention. The result was a **14× reduction in testing time**. More importantly, it shifted how teams thought about field validation. **“Lab simulations are useful, but real-world testing tells you the truth,” he would often point out. Environmental factors like vegetation, air quality, or building density rarely matched lab conditions. His insistence on real-world data improved network reliability and forced teams to confront gaps in their assumptions.*## Multimedia and 5G Saleem also led efforts to demonstrate **5G multimedia streaming** at **26 GHz and 39 GHz** bands. These live demos involved transmitting **4K and 8K video** over directional links — a technically demanding task that revealed issues like line-of-sight sensitivity, multi-base station synchronization, and OS-specific bugs. His role was to ensure these demos worked **end-to-end**, across devices, networks, and platforms. It was an example of how deep technical expertise, combined with disciplined execution, enables innovation at scale. ## Navigating Large Organizations Saleem is candid about the realities of working inside large technology companies. Technical excellence is essential, but **organizational dynamics** play a major role. Promotions often lead to managerial tracks, where technical work is replaced by politics and coordination. He consciously chose to remain on the engineering track, focusing on building systems rather than managing teams. **“If you’re technically strong, the system will always need you,” he says. “But at some point, you peak at a certain engineering level.”## Mentorship and Leadership Saleem spent time as an **educational leader** for Nokia, mentoring interns. He highlights the rewarding nature of seeing their mentees go on to successful careers, often earning more money and securing better jobs than they had. He stressed that having a non-traditional degree (like a BA or a Mining Engineering degree) is not a barrier in the US corporate culture if one is enthusiastic and performs well. He reflects on his career trajectory, explaining why he **chose not to move into managerial roles** despite reaching the top of the technical ladder. He **disliked corporate politics**, which became more intense at higher managerial levels. Although there is some politics in technical roles as well, he emphasized that **strong technical skills make one indispensable**. This dislike for politics ultimately shaped his decision to remain in technical and innovation-driven roles rather than pursuing senior management positions. Saleem’s manager once encouraged him to move into a managerial position, given his years of experience and technical strength. Saleem declined. He explained that he preferred solving problems directly rather than managing people or politics. His exact phrasing was: ****“**I told him**, I can talk to machines. I can’t talk to people.”**## On Programming (C Language) and Embedded Systems When asked about their favorite aspects of **C programming**, Saleem explains: - His work started off mostly on **embedded systems**, with limited memory and processing power. - Libraries and high-level abstractions common on PCs were not feasible; instead, **efficient C and assembly** were required to work with microcontrollers like **Motorola 68040** and **PowerPC**. Over time, they worked across many domains — **electrical engineering, mechatronics, robotics**, and software — before finding their niche. ## Reflections on Skills, Innovation, and Workplace Realities **Innovation is self-driven**: No one told Saleem to innovate; he identified inefficiencies and built better solutions. To **stand out as an engineer**, one must: - Be proactive in problem-solving. - Strive for the **“best way”** among many possible solutions. Saleem recalled his early days manually calculating throughput line by line in terminals before automating testing, which drastically improved speed and efficiency. **"I'll tell you clearly, from my experience, your boss will never tell you to innovate... No one ever told me, this isn't good, do this, do that, it'll be so much better. No! I have a nerdy habit, if I am doing something redundant, I get bored... and then I automate it!"## Global Standards, Academia, and Technological Roots Saleem briefly traced **technological foundations**: - Mentioned **Orthogonal Frequency Division Multiplexing (OFDM)**, **cosine transform** (core of JPEG), and figures like **Dr. K. R. Rao** (University of Texas at Arlington), his supervisor, whose work became industry standards. - Standards compliance involves massive, detailed requirement PDFs that all vendors must follow. Saleem emphasize how **industry builds on academic research**, but commercialization requires strict global standardization. ## Observations from Home After returning to Pakistan, Saleem continued working remotely for US companies. Eventually, **taxation issues and unreliable infrastructure** made it unsustainable. He has been clear in his assessment of the local tech landscape: Pakistan remains in a **catch-up phase**, often competing on cost rather than building ecosystems. In contrast, India’s early investments in infrastructure and capability have allowed it to leap forward. ## Takeaways Saleem’s career offers practical lessons for engineers and organizations alike: - **Anchor in Focus, Innovation, and Quality.** These principles scale. - **Automate wherever possible.** If a task is repetitive, make it disappear. - **Validate in the real world.** Simulations have limits. - **Stay technically sharp.** Strong engineers shape products as much as managers. - **Adapt to structures but don’t be consumed by them.** His journey reflects how sustained technical excellence, applied consistently over decades, can shape industries — often without fanfare. *One with the team. ### [Full Stack Deployment: Setting Up CI/CD for Node.js Applications on AWS with Custom Domains](https://grayhat-company-blog.grayhatstudio.workers.dev/blog/full-stack-deployment-setting-up-ci-cd-for-node-js-applications-on-aws-with-custom-domains) - Slug: `full-stack-deployment-setting-up-ci-cd-for-node-js-applications-on-aws-with-custom-domains` - Published: 2025-05-13T15:00:41.000+05:00 - Updated: 2025-05-13T15:00:41.000+05:00 - Reading time: 9 min - Tags: DevOps, Cloud, Automation, Deployment, Development, Software Engineering, Amazon Web Services (AWS) - Authors: Syed Abdullah Nasir - Visibility: public 💡This is a repost from Abdullah's original blog on Medium. Check it out here: https://medium.com/@nasirabdullahsyed/full-stack-deployment-setting-up-ci-cd-for-node-js-applications-on-aws-with-custom-domains-8924217cb1a4In today’s competitive digital landscape, the ability to deploy applications quickly and reliably is essential for development teams. This comprehensive guide will walk you through establishing a professional CI/CD pipeline for Node.js applications on AWS EC2, complete with custom domain configuration. Whether you’re a solo developer or part of a larger team, these automation techniques will streamline your workflow and ensure consistent deployments. # Understanding CI/CD and Its Benefits Continuous Integration and Continuous Deployment (CI/CD) revolutionizes the software development lifecycle by automating testing and deployment processes. Instead of manually transferring files and restarting services, a well-configured CI/CD pipeline handles these tedious tasks automatically when you push code changes to your repository. The benefits include: - Reduced human error during deployments - Faster release cycles - Consistent testing before production deployment - Easier rollbacks when issues arise - Better collaboration within development teams # Prerequisites Before we dive into implementation, ensure you have: - An active AWS account with permissions to create and manage EC2 instances - A Node.js application ready for deployment (either existing or new) - A GitHub repository containing your application code - A domain name (if implementing the custom domain section) # Part 1: Setting Up Your AWS Infrastructure # Launching an EC2 Instance Let’s begin by creating the server that will host your application: - Log in to your AWS Console and navigate to the EC2 Dashboard *****AWS EC2 Dashboard****- Click the “Launch Instance” button - Select an appropriate Amazon Machine Image (AMI). For Node.js applications, Ubuntu or Amazon Linux 2 are excellent choices due to their stability and widespread support *****EC2 Launch Instance Section 2 — Application and OS Images (Amazon Machine Image)****- Choose an instance type. For smaller applications or testing environments, the free-tier eligible t3.micro is sufficient. Production applications may require more resources depending on traffic expectations *****EC2 Launch Instance Section 3 — Instance type****- Configure a key pair. This is critical for secure SSH access to your instance. Either create a new key pair or select an existing one, but ensure you download the private key file (.pem) if creating a new one *****EC2 Launch Instance Section 4 — Key pair (login)*********EC2 Launch Instance Section 4.1 — Key pair (login) — Create key pair Popup****- Configure security groups to allow the necessary network traffic: - SSH (port 22): Restrict to your IP address for security - HTTP (port 80): Allow from anywhere (0.0.0.0/0) - HTTPS (port 443): Allow from anywhere (0.0.0.0/0) *****EC2 Launch Instance Section 5 — Network settings****- Configure storage settings: - For most Node.js applications, the default storage allocation (8 GB) is sufficient - Use General Purpose SSD (gp2 or gp3) for balanced performance - Consider increasing storage if you anticipate **storing large media files**, **accumulating extensive logs**, **hosting databases locally (though a separate RDS instance is recommended for production) - **You can always increase storage later if needed *****EC2 Launch Instance Section 6 — Configure storage****- Launch the instance and note the Public IP address assigned to it *****EC2 Launch Instance Section 8 — Summary*********EC2 Instance Tab****# Setting Up the Server Environment After launching your EC2 instance, you’ll need to install the necessary software: - Connect to your instance via SSH: *****EC2 Instance — Connect Section — SSH Client Tab****ssh -i /path/to/your-key.pem ubuntu@your-ec2-public-ip - Update the package repositories: sudo apt update - Install Node.js and npm: sudo apt-get install -y nodejs - Install Nginx to act as a reverse proxy and check its status: sudo apt-get install nginx sudo systemctl start nginx sudo systemctl enable nginx sudo systemctl status nginx - Install PM2, a process manager that will keep your Node.js application running: sudo npm install -g pm2 At this point, navigating to your EC2 instance’s public IP address *http://your-ec2-public-ip/* in a browser should display the default Nginx welcome page, confirming that your web server is working correctly. # Part 2: Configuring GitHub Actions for CI/CD GitHub Actions provides an elegant way to implement CI/CD directly within your GitHub repository. We’ll set up a workflow that automatically deploys your application whenever changes are pushed to the main branch. # Setting Up a Self-Hosted GitHub Runner Unlike GitHub’s cloud-based runners, a self-hosted runner gives you direct access to your EC2 instance during deployment: - In your GitHub repository, navigate to Settings > Actions > Runners. *****GitHub Repository Settings — Actions Tab****- Click “New self-hosted runner” - Select “Linux” as the operating system. - Follow the provided instructions to download, configure, and run the GitHub Actions runner on your EC2 instance. *****GitHub Repository Settings — Actions Tab — New Runners Setup****Once installed, set up the runner as a system service to ensure it runs continuously: cd ~/actions-runner sudo ./svc.sh install sudo ./svc.sh start Verify that the service is running: sudo ./svc.sh status # Creating the GitHub Actions Workflow Now, create the workflow definition that will trigger your deployments: - Add your applications environment variables as a GitHub Secret *****GitHub Repository Settings — Secrets and Variables Tab*********GitHub Repository Settings — Secrets and Variables Tab — New Repository Secret Setup****- In your repository, create a directory structure .github/workflows/ - Add a file named deploy.yml with the following content: name: Node.js CI/CD # Trigger the workflow on pushes to the "main" branch on: push: branches: [ "main" ] jobs: build: # This job runs on your self-hosted runner runs-on: self-hosted steps: # Step 1: Checkout the latest code - uses: actions/checkout@v4 # Step 2: Setup Node.js environment - name: Use Node.js 20.x uses: actions/setup-node@v3 with: node-version: '20.x' cache: 'npm' # Step 3: Install dependencies - run: npm ci # Step 4: Set up environment variables # This step assumes you've stored your env variables as GitHub Secrets - run: | touch .env echo "${{ secrets.PROD_ENV }}" > .env # Step 5: Build the project if needed - run: npm run build --if-present # Step 6: Restart the application using PM2 - run: pm2 restart node-app || pm2 start server.js --name node-app This workflow performs several important functions: - Checks out your code on the EC2 instance - Sets up the appropriate Node.js version - Installs dependencies with npm ci (which is faster and more reliable than npm install) - Creates an environment file with your secrets - Builds your application if needed - Starts or restarts your application with PM2 # Configuring Nginx as a Reverse Proxy Now, set up Nginx to direct incoming web traffic to your Node.js application: sudo nano /etc/nginx/sites-available/default Replace the default configuration with: server { listen 80; server_name _; # For API endpoints location /api { rewrite ^\/api\/(.*)$ /api/$1 break; proxy_pass http://localhost:4000; # Adjust port to match your application proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; } } Test the configuration and restart Nginx: sudo nginx -t sudo systemctl restart nginx # Part 3: Adding a Custom Domain A professional application should have a proper domain name rather than an IP address. Let’s configure your application to use your custom domain. # Setting Up DNS Records - Log in to your domain registrar’s dashboard (e.g., Namecheap, GoDaddy, Route 53). - Navigate to the DNS management section for your domain. - Create A records pointing to your EC2 instance: - Type: A Record - Host: @ (for root domain) - Value: Your EC2 instance’s public IP address - TTL: 3600 (or recommended value) - For the www subdomain: - Type: A Record - Host: www - Value: Your EC2 instance’s public IP address - TTL: 3600 # Updating Nginx Configuration for Your Domain - Create a new Nginx configuration file for your domain: sudo nano /etc/nginx/sites-available/default - Add the following configuration: server { listen 80; server_name your-domain.com www.your-domain.com; # For API endpoints location /api { rewrite ^\/api\/(.*)$ /api/$1 break; proxy_pass http://localhost:4000; # Adjust if needed proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; } # For serving static content or frontend location / { proxy_pass http://localhost:4000; # Adjust if needed proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; } } - Enable the new configuration: sudo ln -s /etc/nginx/sites-available/your-domain.conf /etc/nginx/sites-enabled/ sudo nginx -t sudo systemctl restart nginx # Securing Your Application with SSL/TLS Adding HTTPS encryption is crucial for modern web applications: - Install Certbot and the Nginx plugin: sudo apt update sudo apt install certbot python3-certbot-nginx - Obtain and install SSL certificates: sudo certbot --nginx -d your-domain.com -d www.your-domain.com - Follow the prompts to complete setup, choosing to redirect all HTTP traffic to HTTPS. - Certbot automatically configures renewal, but you can test it: sudo certbot renew --dry-run After SSL configuration, your Nginx setup will be updated to handle HTTPS connections securely. # Part 4: Verifying and Testing the Deployment After completing the setup, it’s time to verify that everything works as expected: - Push a change to your repository: git add . git commit -m "Test CI/CD deployment" git push origin main - Monitor the GitHub Actions workflow in your repository’s Actions tab. - Once the workflow completes, visit your domain or EC2 public IP address to verify that your application is running correctly. - Check the PM2 status on your EC2 instance: pm2 status # Advanced Optimizations To further enhance your deployment, consider these advanced optimizations: # Allocating an Elastic IP An Elastic IP ensures your application remains accessible even if your EC2 instance is restarted: - In the AWS Console, navigate to EC2 > Elastic IPs. - Allocate a new Elastic IP address. - Associate it with your EC2 instance. - Update your DNS A records to point to this new Elastic IP. # Implementing a CDN For applications serving users across different geographic regions, a CDN can significantly improve performance: - Set up AWS CloudFront or another CDN service. - Configure the CDN to use your domain as the origin. - Update your DNS records to point to the CDN distribution. # Setting Up Monitoring and Logging Implement monitoring to stay on top of your application’s health: - Install a monitoring agent like AWS CloudWatch or set up Prometheus. - Configure alerting for critical metrics like CPU usage, memory utilization, and disk space. - Set up centralized logging with tools like CloudWatch Logs, ELK Stack, or Graylog. # Common Troubleshooting Tips If you encounter issues during setup, check these common problem areas: - **DNS Resolution Issues**: Use nslookup your-domain.com to verify DNS propagation. - **Connection Refused Errors**: Check that your security groups allow traffic on the necessary ports. - **Application Not Running**: Check PM2 logs with pm2 logs node-app. - **Nginx Configuration Problems**: Review error logs with sudo tail -f /var/log/nginx/error.log. - **SSL Certificate Issues**: Ensure that Certbot completed successfully and check for certificate errors in browser developer tools. # Conclusion You’ve now set up a professional-grade CI/CD pipeline for your Node.js application on AWS EC2, complete with a custom domain and HTTPS encryption. This automation will save you countless hours of manual deployment work while ensuring consistent and reliable updates to your application. By leveraging GitHub Actions, you’ve created a streamlined workflow that automatically deploys your code whenever changes are pushed to your repository. This approach facilitates rapid iteration and helps maintain a consistent development experience across your team. The addition of a custom domain with SSL/TLS encryption provides a professional appearance and ensures secure communication between your users and your application. Remember to maintain your infrastructure by keeping your server updated and monitoring your application’s performance. For more advanced scenarios, consider exploring container-based deployments with Docker and Kubernetes, which can provide even greater flexibility and scalability for complex applications. Happy coding and deploying! ### [Pixels to Players: How Good Game Designs are Executed](https://grayhat-company-blog.grayhatstudio.workers.dev/blog/pixels-to-players-how-good-game-designs-are-executed) - Slug: `pixels-to-players-how-good-game-designs-are-executed` - Published: 2024-08-14T23:04:07.000+05:00 - Updated: 2024-08-15T11:11:02.000+05:00 - Reading time: 6 min - Tags: Game Design, Product Design, System Design, Design, Gaming, Multiplayer Gaming, Playroom, PlayroomKit, Development, Software Engineering - Authors: Maaz Tariq - Visibility: public ** Great video games are like great books or movies; they resonate with us because they reflect our own experiences, dreams, and fears Like a composer crafting a symphony or a painter stroking onto their canvas, designing a game is a similar creative endeavour to any other art. There are no ways to design a game and a million ways to create one simultaneously. Making a good game is like making a good movie, it is supposed to be an experience one goes through that leaves an impact and gives a new perspective. Crafting together a piece of media that can deliver enough sentimental value to keep players coming back, that is what game design is all about. ## Making your Game Relatable One of the key aspects of making a moving art piece is adding elements in the piece that help the audience relate to it. When one sees another character going through situations they have gone through in real life, it develops a bond with the character. This pattern is commonly seen with anime protagonists having very relatable personality traits or situations in even a supernatural world. ** It should be the experience, that is touching. What I strive for is to make the person playing the game the director ***- Shigeru Miyamoto*** *****Papers, Please****Invoking that feeling of relatability is a key part of keeping the players coming back. A good example of executing this strategy is “Papers, Please”. To say very loosely, it's a game about checking and approving documents. A very simple premise, but it is a hit game because the way it sets the mood and develops the scene is very natural. It reminds you of a paperwork-heavy office, it makes you feel like an actual clerk with all the tediousness that comes with it. flipping through pages to check for rules, the applicant’s documents missing or fraudulent cards and ID cards and you have to manage all this junk under a time limit. The authenticity of the experience sells the game. *****Katana Zero****The experience we want to invoke is not limited to experiences our player has personally experienced but also seen others experience in their vicinity. The video game “Celeste” does an excellent job of explaining what depression feels like to people who haven’t experienced it, helping them understand people who suffer from depression. “Katana Zero” is a game with an excellent storyline. It explains the struggles of a soldier dealing PTSD in a very supernatural, ongoing conspiracy theory setting. After going back and forth with some product teams, I've learned that this goes hand-in-hand with KYC (Know Your Customer). Something which might help you to narrow down an idea is to first do some bare-bone **audience research. **Who is the target audience you have the most access to, whether in your friends circle, community, or in your company's easiest access? What is daily life for them, what is entertainment, what makes their heads turn? Just some raw data from here, organized and transformed into a "player persona", can act as a prompt for you to brainstorm some better ideas - Then you can easily validate or verify your ideas by just bouncing them off of that persona. (you can even reach out to an audience member and present ideas to them) ## Using the Right Tools Invoking experience is one of, if not the greatest, priorities for a game designer. The designer must have tools capable enough to pull off the ideas they draft. A designer’s canvas is the engine they use. The way you cannot achieve on a smaller canvas what you can on a larger one. You cannot do things on an engine that is incapable of following through with the mechanics of your design. More often than not, the development-end of game-building is almost as artistic as the design side. It makes sense, given that you need to create a world which truly captures the emotion conveyed in the game, or at least having enough helpful snippets which can keep the code clean while building out the game. This usually drives companies to build custom game engines, or at least base them off of existing ones. Many times, technological advances are the reason for designing new experiences to human entertainment. Grayhat's npm package "create-multiplayer-game" is built to speed up the development process and simplify implementing game designs. We use it thoroughly when building out game prototypes - However, by the time the game reaches production, the engine does take a beating. But we use the new findings to improve the engine once more. The package aims to streamline the creation of React-based (more coming in the future!) multiplayer games, making it easier for developers to focus on the creative aspects of game design rather than being limited by technical challenges. *create-multiplayer-game (CMG) does lots of heavy lifting for you. It provides you with prebuilt modules so you don’t have to reinvent the wheel every time. CMG provides a silent router, letting you change game phases without any changes in the URL bar. This makes the game-flow entirely in control of the game itself and handles the possibility of cheating by messing with the URL to switch phases. It also has its own loading module which can show what file is being loaded in real time. All in all it has the essential parts of a video game for any kind of game prebuilt, so you can focus on the design instead of the execution. ## Learning from Retrospective “Meme, Chat, Robots” has a user interface and design similar to Meta apps. When talking about the game with Saad Bazaz, I learned Meme, Chat, Robots’ UI was designed by a talent at Meta. Using Radix, helps us make reusable components that can be used throughout the project, giving it a coherent look and feel. Addition of a silent react-router, one that can route to different pages without showing changes in the URL. While seemingly a small change, it makes a substantial difference for video games. A video game has to follow a game flow, unlike apps where users can go to whatever page they like. moving from stage 1 to stage 2, or from a cut-scene to gameplay requires a game flow that cannot be tampered with from the URL. ## Get Your Hands Dirty As a game designer, your tools are the technologies and languages you build games with and your canvas is the game engine you use. To translate your designs into the game, you will have to know how the game works. How it's built and why it does what it does. You can’t get away with skipping learning a phase of development, learning development helps the design be grounded and realistic. *## Recycle your Trash There’s no such thing as bad ideas. I have used parts of stories and themes I wrote in my high school essays in complete products! Stories and ideas that don’t seem like a good fit are just in the wrong place. Always save your drafts and keep them close whenever you want to brainstorm a new theme or look for your game. Have different folders for all kinds of media you draw inspiration from, then try to fit them to any future projects. Make different folders for music and art and keep adding any ideas in those folders. ** The first mark on an empty canvas is the most difficult to make Having a stash of resources like these help you form your first stroke on a blank canvas. ## Verdict As daunting as designing a video game may seem, following only a couple of principle can guarantee an interesting result. Trial and error is part of the game, like any design process. Pair it with some direction and you’re good to go! Here’s a small recap: - Design the experience, not the app - Bind real-life experiences with the video game’s experience - Use a capable game engine, that fits your game aesthetic and can pull off your design - Learn and apply from previous projects, embrace failure - Learn and experience every part of the dev process firsthand Now building the latest video game, I have learnt a few more lessons to help me contribute to CMG. Stay tuned for more in-depth articles discussing game design and CMG! ### [Building a Unity Plugin in JavaScript](https://grayhat-company-blog.grayhatstudio.workers.dev/blog/building-a-unity-plugin-in-javascript) - Slug: `building-a-unity-plugin-in-javascript` - Published: 2024-05-04T14:21:06.000+05:00 - Updated: 2024-08-31T13:07:31.000+05:00 - Reading time: 6 min - Tags: Development, Gaming, Multiplayer Gaming, Software Engineering - Authors: Talha Momin - Visibility: members **Playroom for Unity is open-source. Check it out here: https://github.com/asadm/playroom-unity**Interested in trying out Playroom for Unity? Check the docs! Join the Discord channel too in case you need help, you'll find me lurking there sometimes. 😁Creating a game is no easy task, and crafting a multiplayer experience adds an even greater level of difficulty. But thanks to industry experienced developers who've created numerous tools which make the process of creating multiplayer games easier and more productive, developers can now focus on creating fun and immersive experiences for their users, and not worry about the networking side. One growing platform for this purpose is PlayroomKit by Playroom, which mainly focuses on multiplayer web-based party games. I'm a Unity Developer, so I've had my eyes on similar multiplayer plugins for quite a while. Some of them are: - **Normcore:** https://normcore.io/ - **Photon:** https://assetstore.unity.com/packages/tools/network/photon-unity-networking-classic-free-1786 - **PlayFab:** https://learn.microsoft.com/en-us/gaming/playfab/features/multiplayer/lobby/lobby-matchmaking-sdks/multiplayer-unity-plugin-quickstart - **Hathora:** https://hathora.dev/ One of my biggest complaints (and the community's) is how hard it is to get things up and running with these libraries. All that previous knowledge helped me, when I had to implement a plan to create PlayroomKit for Unity, keeping the objective in mind, making sure I didn’t hurt Developer Experience, and using my knowledge in Unity and hacking around in C# and JS. ### The Goal **Combine the ease of PlayroomKit with power of the Unity engine.The PlayroomKit package is super simple to get started with… in JS, at least. That’s a developer experience we needed to port to Unity. At the same time, we had to make the Unity library at feature parity with the JS library, following the exact same API. (That makes it easier to write docs, at least 😃) Here our first **problem** arises which is quite easy to pinpoint: Unity uses C# and PlayroomKit is a JavaScript package. So some interoperability had to occur. To achieve this, we had the following approaches: - Convert the JS library to C#, or, - Use a JavaScript Interpreter for .NET (JINT), or, - Use the Interaction with browser scripting provided by Unity itself. **If you want to go deeper into the thought process of “why” we went with our final approach, I highly recommend reading Playroom’s official blog on this very topic.### The Approach We went with the **third approach**, referring the Unity docs. In short, the workflow is like this: - We work with 2 files: a JSLIB (JavaScript Library) and C# class. - The JSLIB file acts as a bridge between PlayroomKit (or any other JS library) and C# (Unity) *What I call "The Bridge".The figure above shows basic working of the system. ### Problem 1: Passing Data The Unity documentation shows an example where the primitive datatypes are being used to pass data between C# and JS. This process of converting is known as: ***Marshalling.** This process involves converting an object's memory representation into a format suitable for storage or transmission, especially across different runtimes.*The documentation gives us a good starting point with examples for the basic datatypes: Hello: function () { window.alert("Hello, world!"); }, HelloString: function (str) { window.alert(UTF8ToString(str)); }, PrintFloatArray: function (array, size) { for(var i = 0; i > 2) + i]); }, AddNumbers: function (x, y) { return x + y; }, StringReturnValueFunction: function () { var returnStr = "bla"; var bufferSize = lengthBytesUTF8(returnStr) + 1; var buffer = _malloc(bufferSize); stringToUTF8(returnStr, buffer, bufferSize); return buffer; }, And in C# we will define the functions like this: [DllImport("__Internal")] private static extern void Hello(); [DllImport("__Internal")] private static extern void HelloString(string str); [DllImport("__Internal")] private static extern void PrintFloatArray(float[] array, int size); [DllImport("__Internal")] private static extern int AddNumbers(int x, int y); [DllImport("__Internal")] private static extern string StringReturnValueFunction(); To use these functions, we can call them like so: void Start() { Hello(); HelloString("This is a string."); // sending a string to JS float[] myArray = new float[10]; PrintFloatArray(myArray, myArray.Length); int result = AddNumbers(5, 7); Debug.Log(result); Debug.Log(StringReturnValueFunction()); }Now this is all great, but the issue arises when we have to deal with async code or functions with callbacks. ### Problem 2: Async Code or Callbacks?! There are great discussions on the Unity Forums regarding using async functions and for passing callbacks as well. In the case for PlayroomKit, instead of using async / await, we went with providing callbacks, (PlayroomKit already provides callback parameters wherever required). The pattern here is something like so: ### [Reject Cloud, return to onprem](https://grayhat-company-blog.grayhatstudio.workers.dev/blog/reject-cloud-return-to-onprem) - Slug: `reject-cloud-return-to-onprem` - Published: 2024-02-29T12:03:00.000+05:00 - Updated: 2024-08-17T13:24:35.000+05:00 - Reading time: 6 min - Tags: Software Engineering, Cloud, Infrastructure, DevOps - Authors: Saad Bazaz - Visibility: public Remember when you could easily spin up a gaming server on your dusty ahh Pentium 4 desktop, and play with people around the world? Honestly, I don't. I couldn't really figure that out with the crusty internet speeds I had, all the blockades on our Internet here, and the learning curve was way too high. ## My self-hosting journey **You merely adopted the Cloud. I was born into it, moulded by it.I ran LAN parties back in school. My friends and I would load all the lab PCs with Counter Strike 1.6, and play the heck out of the hottest summer days. In uni, one of my laptop's broke apart (it was stepped on), and since I'm not a wasteful guy, I created a Linux-powered mediaserver out of it which I streamed movies off of using Samba, giving me almost unlimited storage and my own personal cinema. I got into self-hosting. I ran SSH off of my broken laptop, and used to build projects on it, using my good laptop as simply a "portal". I then stumbled upon **CapRover**** **in it's early stages, and I absolutely loved it. I deployed a few apps, crashed a lot of stuff, but it was cool in general. Then came **Coolify**, and I haven't let it go so far! ## What's going on in the Cloud world?! **TLDR; The Big Cloud Exit is very real.Even though Cloud, Cloud Native and IAAC are on the rise, there's a continuous increase in unnecessary complexity and overhead, which pretty much kills the case for simpler use cases. There seems to be a two factions - Cloud-only and on-premises - but they seem to be united by similar technologies (Containerization, modularity, etcetera.) ### The Olden Days Let's start with a bit of history. Before Gen Z and millennials got into software, baby boomers had a very distinct sales strategy. Build once, sell once. You pay $200, you own a license to the software, and now it's yours. It's installed on your computer and you can do whatever the heck you want to do with it. This process, albeit slow, had it's charms. Software had to be built right the first time before sales started, which resulted in pretty stable software for its time. For instance, you couldn't just send an update of your game to the Nintendo Gameboy. The cartridge had to be flashed once. The only way to update was a complete recall, like when Nintendo recalled Pokemon cartridges back in the early 2000s. As peer-to-peer arose in popularity, so did Tor. Piracy and illegal filesharing called for a need to "centralize" a software's control points. These pointed to having a remote server, most likely in the software's creators office. This gave rise to the subscription model. (Although, despite many misconceptions, the subscription model existed before as well in the form of mail-in CDs, USBs, etcetera). Then arose an interesting proposal: What if all these software creators centralized their centralized servers even further?! This lead to mass-scale Cloud providers like Microsoft, Google, Amazon, and more. Today, Amazon Web Services (AWS) stands as the largest cash producer in Amazon's portfolio. ### Fast forward The costs of subscriptions just keep adding up. The software company owning the SaaS tool you use, is further paying subscription to another service, which is further paying subscriptions to another, and finally at the end of the chain is a company which is burning VC money like crazy just to keep **their **subscription costs at the lowest. Sounds familiar? ▲ For the sake of comparison, here's the subscription cost of running a software agency of 15 people, on modern SaaS tools: *Costs with ALL SaaS SubscriptionsNow eradicate some costs with self-hosted options: *Costs with some SaaS Subscriptions, mixed with self-hostingYes, obviously the saving you're getting will probably be spent on **electricity, hardware, maintainers, **and **backups.** **Still, **when you're paying $15k a year for just the tools under your belt, you gotta step back and think; "Why don't I own the software at this point?" Surely, $15k (or even a fraction of it) in share values HAS to add up to something. Plus, there's always a chance of screwing up with a memory leak somewhere (like this user who made the same sad mistake), or the risk of being DDoS'ed, which can surge your Cloud bill to $104,000 (like this Netlify user) just overnight. What's the point of a Cloud and all its services, if you can't have a good night's sleep? This sentiment, along with tonnes more surrounding privacy, performance, and peace, have driven self-hosted enthusiasts around the world to build a new business model for the sustainability of the tech world. ## "Self-hosted" as a business model Some major and minor events in the self-hosting world: - 37signals announces Once.com with their first pay-once-own-forever software, CampFire. Their manifesto is an excellent read, and they've been advocates of Quitting Cloud for quite some time. - Plane.so, open source task management software reaches 22k stars on GitHub in less than a year - Coolify, the absolute king of self-hosting management, has more than 15,000 self-hosted instances. - Medusa.js, possible the biggest self-hosting of all marketplaces, reaches 20k stars on GitHub - Microsoft ditches Azure (their own Cloud) for LinkedIn (their own product) We're seeing two trends clearly - Either go full in Cloud, or allow people to self-host. This spawns an entirely new business model; host yourself for free, or host on our Cloud for $$. What does this mean for new startups and businesses? In fierce competition, letting people self-host with a strong license means you can: - Get your product tested, verified easily by a large number of users. Use the feedback to build better - Remove privacy and security concerns, improve trust on your product - Resolve DevOps problems - Get bugs fixed and features created through the community - Get Viral. Get promoted for pretty much free through just some good DevRel, and get tonnes of appreciation ## Self-hosting as a Tech Startup ***Mantra: *You can't call yourself a Cloud or DevOps engineer unless you can run an on-prem server and maintain it for a minimum of 3 months.Let's talk real benefits for startups, other than making their business model self-hosted. What can you get done with a self-hosted, on-premises system in your workplace? - **Expendable dev servers. **Save the cost of Google Cloud for staging and dev servers. - **Build runners, CI/CD. **The boring stuff, the compute-consuming stuff. - **Business Development and Sales automations. **Business operations with expendable data, which are usually stateless and just need to be "listening" somewhere (Examples: Scrapers, Bulk emailers) - **Process automations** (Examples: Stateless Slack Bots, Discord Bots, Builder Bots, Automated Changelog Updates. You name it.) - No **data privacy** concerns (if you apply the right security practices!) - **Monitoring** (Example: Checking system healths for projects, checking your baby monitor) - Learn how to **get your hands dirty**. Clouds often have fancy names for pretty basic stuff in almost any onprem system. It's good to know their origins, as it helps you make better Cloud deployments, and can improve your engineering culture too. *By the way, I'm not **against Cloud. **I just encourage people to know what they're doing, and to use the right tool for the right job. Knowing the basics of building onprem systems is crucial in a Cloud Native world.* ## Resources What are the best places to learn self-hosted, and to get guidance? - Discord servers: As always, you'll find the best of the best basement dwellers lurking around on Discord. There are tonnes of self-hosting communities who can guide you on the basics. I particularly love Coolify's community, but I'm sure you'll find more on top.gg - The Awesome Self-Hosted list - The r/servers subreddit - The r/selfhosted subreddit - This cool blog I found - ChatGPT The list I have is exhaustive, but if you have more suggestions, drop a comment and I'll add it up! ## What's next We're building on-prem AI systems for Omni. Why? - Unrealistic GPU costs on the Cloud - Hybrid architecture: We want Omni to be deployable anywhere for quick processing, so we need to ensure resources are used the right way During this, we've figured out some pretty good ways to make teams more efficient while easily saving around $3000 annually. I call it "WorkStack". I'll be publishing a guide soon on **WorkStack**, and how you can use it in your org to save you some costs. Plus, expect some **open-source goodies **to help you along the way. Happy hacking! ⚡️ *We love doing things differently, and contributing to the overall knowledge stream. A lot of our work is R&D-based and on experimental tech in application development and Artificial Intelligence. If you're interested in working with *Grayhat*, DM or comment!* **This article was authored by** Saad Bazaz, **Chief Executive Officer at Grayhat. Special thanks to **Muhammad Hashim **for his research on the topic, and **Sohaib Bazaz** and **Muhammad Saad** for their work on Baadal, Grayhat's on-premises infrastructure.** ### [The Evolution of SecOps, DevOps, DevSecOps, GitOps, and Developer Experience](https://grayhat-company-blog.grayhatstudio.workers.dev/blog/the-evolution-of-secops-devops-devsecops-gitops-and-developer-experience) - Slug: `the-evolution-of-secops-devops-devsecops-gitops-and-developer-experience` - Published: 2023-09-06T16:34:00.000+05:00 - Updated: 2024-05-09T16:35:52.000+05:00 - Reading time: 3 min - Tags: DevOps, GitOps, SecOps, Software Engineering - Authors: Syed Abdullah Nasir - Visibility: public *OctokittyOpsIn the fast-paced world of software development, staying ahead of the curve is essential. As build times shorten, Sprint cycles shorten, and remote culture rises, the management of the Software Development Lifecycle is rapidly being transferred from the hands of managers into the hands of developers themselves. Auditing by a manager is no longer a one-time thing; metrics of software quality like security, performance, code quality, and testing have been delegated to the developers themselves. The base unit is now the Pull Request - whenever a chunk of code is added to the main code, it's the team's responsibility to ensure it's good code. This allows developers to consistently improve all the metrics and have a "history" of quality. Five crucial concepts have emerged in recent years, revolutionizing the way software is developed, secured, and managed. These concepts are SecOps, DevOps, DevSecOps, GitOps, and Developer Experience (DX). In this article, we will explore each of these practices and their significance in modern software development. **SecOps** SecOps, short for Security Operations, has become indispensable in today's digital landscape. It encompasses the integration of security practices into the operations of the software development process. The primary goal is to fortify software security by ensuring that security is not an afterthought but a fundamental part of the development pipeline. By embedding security practices from the outset, SecOps minimizes vulnerabilities and strengthens defenses against cyber threats. **DevOps** DevOps, a portmanteau of Development and Operations, is all about fostering collaboration and automation within a software development team. It aims to bridge the gap between developers and operations teams, enabling faster development cycles and improved software quality. DevOps practices include continuous integration, continuous delivery, and infrastructure as code, creating a streamlined and efficient development process. **DevSecOps** DevSecOps takes the principles of DevOps and adds a crucial layer of security. In today's threat landscape, security cannot be an afterthought. DevSecOps integrates security measures throughout the entire DevOps pipeline, ensuring that security is woven into every stage of development. This proactive approach reduces the risk of vulnerabilities and data breaches, making it a vital practice for safeguarding software in the digital age. **GitOps** GitOps leverages the power of version control systems, most notably Git, to manage and automate the deployment, configuration, and monitoring of applications and infrastructure. By treating infrastructure as code and using Git repositories as the single source of truth, GitOps simplifies and streamlines the management of complex systems. This approach enhances traceability, transparency, and collaboration among development and operations teams. **Developer Experience (DX)** Developer Experience, or DX, is about creating an environment that empowers developers to do their best work. It encompasses everything from user-friendly development tools and documentation to efficient workflows and supportive team dynamics. A positive DX leads to increased developer productivity and innovation, making it a critical factor in attracting and retaining top talent in the competitive software industry. **The Synergy** When these five concepts—SecOps, DevOps, DevSecOps, GitOps, and DX—are combined, they form a holistic approach to software development and operations. DevOps accelerates development cycles, while DevSecOps ensures that security is embedded from the start. GitOps streamlines deployment and management, while a positive DX enhances productivity and innovation. The interplay between these practices creates a secure, efficient, and enjoyable development environment. ## Why Ops? 1. Efficiency: Streamlining complex software development and operations. 2. Speed: Faster development, deployment, and innovation. 3. Security: Integrating security from the start. 4. Agility: Adapting quickly to changing market demands. 5. Cost Reduction: Optimizing resources and reducing operational costs. 6. Developer Productivity: Enhancing the developer experience to attract top talent. Numerous organizations have successfully implemented these practices to transform their software development processes. From tech giants to startups, the adoption of DevOps, DevSecOps, GitOps, and a positive DX has led to faster delivery of high-quality software with enhanced security features. **Google's DevOps Transformation** Google adopted DevOps principles to enhance its software development and operations. They reduced their average release cycle from months to days, resulting in faster feature delivery and improved service reliability. This transformation allowed Google to maintain its leadership in the tech industry. **Netflix's Continuous Deployment with DevOps** Netflix implemented DevOps practices to achieve continuous deployment. They can now release updates and new features to their streaming platform hundreds of times a day. This rapid iteration keeps customers engaged and satisfied, making Netflix a global entertainment giant. **Target's DevSecOps for Enhanced Security** Target integrated DevSecOps to bolster its cybersecurity efforts. By proactively addressing security vulnerabilities in the development process, they fortified their systems against threats. This approach helped Target rebuild trust with customers after a significant data breach, showcasing the power of DevSecOps in safeguarding sensitive data. **Conclusion** In the ever-evolving landscape of software development, staying updated with these transformative practices is essential. SecOps, DevOps, DevSecOps, GitOps, and DX are not just buzzwords; they represent the future of efficient, secure, and enjoyable software development. Embracing these concepts can help your organization stay competitive and thrive in the digital age. **Author: **Syed Abdullah Nasir