今日已更新 264 条资讯 | 累计 23847 条内容
关于我们

标签:#ux

找到 153 篇相关文章

AI 资讯

Self-Hosting Like a Pro, Part 1: Hardening a Fresh Ubuntu VPS

This is the first article in a four-part series where I document how I turned a 10€/month VPS into a production-grade platform hosting my portfolio, a university group webapplication and a SaaS product, all isolated from each other with Kubernetes. In this part, we take a fresh Ubuntu server and lock it down properly before installing anything else. Why bother with hardening? The moment your VPS gets a public IP address, it starts receiving attacks. Not "might receive", it starts . Within minutes, automated bots will probe port 22, try root:root , admin:admin123 and thousands of other credential combinations. If you skip this step and jump straight to deploying your apps, you are building on sand. The good news: an hour of work is enough to eliminate the vast majority of these threats. Here is what we will set up: A non-root user with sudo privileges SSH key authentication, with passwords and root login disabled UFW as a simple, effective firewall Fail2ban to ban brute-force attackers automatically Automatic security updates What you need A fresh VPS running Ubuntu 24.04 LTS or newer. I use a Hostinger KVM 2 (2 vCPU, 8 GB RAM, 100 GB NVMe), but any provider works: Hetzner, DigitalOcean, OVH, Contabo. The root password or SSH key your provider gave you. A terminal on your local machine (macOS, Linux, or WSL on Windows). Throughout this tutorial, replace YOUR_SERVER_IP with your server's IP address and deploy with the username you want to use. Step 1: First login and system update Connect as root for the first and last time: ssh root@YOUR_SERVER_IP Update everything before touching anything else: apt update && apt upgrade -y apt autoremove -y If a kernel update was installed, reboot now: reboot Wait a minute, then reconnect. Step 2: Create a non-root user Working as root is like driving without a seatbelt: fine until it isn't. One mistyped rm -rf and the party is over. Create a dedicated user: adduser deploy Choose a strong password (you will still need it for sudo ,

2026-07-06 原文 →
AI 资讯

I Built a NATO Phonetic Alphabet Converter After One Phone Call Changed My Mind

It Started With a Simple Misunderstanding I was spelling something over a phone call. I said: "B" The other person heard: "D" So I repeated it. Still wrong. Then I remembered something I'd heard before: "B as in Bravo." Instantly... There was no confusion. That's When I Realized Some letters sound almost identical. Especially over: Phone calls Weak connections Noisy environments Different accents And repeating the same letter five times doesn't always help. Why I Built This Tool So I built something simple: 👉 https://allinonetools.net/phonetic-alphabet-converter/ A tool that instantly converts normal text into the NATO phonetic alphabet. For example: CHAT Becomes: Charlie Hotel Alpha Tango No signup. No setup. Just: Paste → Convert → Read What I Learned Before building this, I thought the phonetic alphabet was mostly for pilots or the military. Turns out it's useful for anyone who needs to spell things clearly. Like: Email addresses Usernames License keys Customer support Phone conversations The Small Problem It Solves Have you ever said: "M" And someone replied: "N?" Or: "P?" 😅 That's exactly the kind of confusion this avoids. Why It Works So Well Instead of similar-sounding letters... You use unique words. Like: A → Alpha B → Bravo C → Charlie D → Delta It's much harder to misunderstand. What Surprised Me I expected only developers or IT people to use it. But it also makes sense for: Customer support Call centers Students Remote workers Anyone spelling things over the phone What I Focused On I wanted the tool to be: Fast Simple Easy to copy Beginner-friendly Because if you're already on a call... You don't want extra steps. The Real Insight Good communication isn't always about saying more. Sometimes it's about making sure the first attempt is understood. Simple Rule I Follow Now If people keep repeating themselves... 👉 There's probably a simpler way to communicate. Final Thought The NATO phonetic alphabet has been around for decades. But after using it once... Yo

2026-07-06 原文 →
产品设计

Missing network configuration on fresh Ubuntu Server offline installation

Installing Ubuntu Server 24.04 LTS in an offline mode (no LAN cable or WiFi connected) leaves you with an unmanaged network interface which requires manual configuration post-install. The interface enp4s0 is unmanaged by systemd-networkd and also the service itself is disabled. NOTE: This guide applies to Ubuntu server. On Ubuntu desktop you have the NetworkManager service installed and the steps would be different. To fix the problem follow the steps below: Create a Brand New Netplan Configuration File Look into /etc/netplan . You will probably see the dir is empty. This means the installer completely gave up on configuring the network and didn't create any profiles. Create a new file, e.g. vim /etc/netplan/01-netcfg.yaml . Paste the following configuration network : version : 2 renderer : networkd ethernets : enp4s0 : dhcp4 : true This makes the interface managed by networkd instead of the desktop NetworkManager. Fix permissions The new file needs to be readable only by root so fix it's permissions chmod 600 /etc/netplan/01-netcfg.yaml . Enable network service Enable the network service and make it start on boot: systemctl enable systemd-networkd systemctl start systemd-networkd Run netplan Finally, we need to tell Ubuntu to use our new configuration and activate the network netplan generate netplan apply Network should be up! ip a

2026-07-05 原文 →
AI 资讯

Reclaim free space from VirtualBox VM on Windows host

When you delete files in your virtualbox VM in order to free up space on the host filesystem, this space is not automatically reclaimed. In order for the host system to see the changes you need to rewrite the free space with zeroes. Follow the below steps to perform this operation: Install zerofree package. It is needed to rewrite the free space with zeroes. Mount the filesystem as "readonly". This is needed for the tool to be able to perform it's task. If you're working with the "/", easiest way to mount it as readonly is to edit the kernel parameters. Edit /etc/default/grub . Find the GRUB_CMDLINE_LINUX_DEFAULT line. Add init=/bin/bash to it reboot Run zerofree -v /dev/sdX . This could run for some time, depending on the size of your disk. After it's done, run exec init to finish booting up. Shutdown the VM in order to be able to run the next command which requires a lock on the VDI volume. On the Windows host run VBoxManage.exe modifymedium "path\to\disk.vdi" --compact

2026-07-05 原文 →
AI 资讯

I Thought I Understood Containers. Then I Tried Building One.

I had just aced my mentor’s Docker exam, so of course I thought I understood containers. I had said all the right words: namespaces, cgroups, images, layers, PID 1, Kubernetes Pods. Then I typed my first serious command and Linux reminded me that knowing the nouns is not the same thing as building the thing. $ sudo unshare -p 1 test unshare: failed to execute 1: No such file or directory That was the opening scene. I had not even built anything yet. I had typed the flags wrong and accidentally asked unshare to execute a program called 1 . This was going to be less “implement Docker” and more “let the kernel correct my confidence, one error at a time.” v1: namespaces, or the first time PID 1 lied to me The first version was supposed to be easy: run a process in a new PID namespace and prove it sees itself as PID 1. So I ran the command the way I thought it worked: $ sudo unshare --pid bash # echo $$ 25184 That was not PID 1. That was just embarrassing. The rule I had missed is simple: PID namespaces apply to children. The process that calls unshare --pid does not magically become PID 1. You need to fork. The first child born into the new namespace becomes PID 1. So the working version was: $ sudo unshare --pid --fork bash # echo $$ 1 That one line changed the tone. I was inside a different process universe. The shell thought it was process 1. Signals felt different. Orphans came home to it. Then I ran ps , and got humbled again. # ps -o pid,ppid,comm PID PPID COMMAND 25310 25304 bash 25344 25310 ps That made no sense at first. I was PID 1, but ps was showing host-looking PIDs. The next reveal: ps does not ask the kernel some pure “what processes exist?” question. It reads files. If /proc still points at the host procfs, your tools will tell you the host story. So I remounted /proc from inside the namespace: # mount -t proc proc /proc # ps -o pid,ppid,comm PID PPID COMMAND 1 0 bash 7 1 ps That was when it clicked. The namespace did not become real to my eyes until /pr

2026-07-05 原文 →
AI 资讯

What Six Arguing AI Agents Taught Me About Building One That Actually Works

I broke my own project on purpose, twice, before it worked. Here's the story. Round one: the debate club My first idea for this hackathon sounded great in my head. Six AI agents, each with a "role" — security, architecture, performance, whatever — and they'd debate each other across multiple rounds before agreeing on a final answer. Like a mini panel of experts arguing it out. I built it. I ran it against some vulnerable test code. It came back with 127 findings. I got excited for about four minutes. Then I actually read them. Maybe three were real. The other 124 were the agents politely agreeing with each other about problems that didn't exist, or restating the same bug five different ways because five different agents happened to notice it. Precision was somewhere around 2%. Worse than a single model working alone. That stung a little, not going to lie. I'd spent days on the debate logic. Round two: quieter, and better So I ripped it apart. No more debate rounds. No more six agents shouting over each other. I went down to four, gave each one exactly one job, and — this is the part that actually fixed things — made them depend on each other in order instead of all firing at once. One agent maps out the code first. Two others use that map to look at security and quality separately. A last one compares what they found, throws out duplicates, and — importantly — actually checks the line numbers against the real file instead of trusting the AI's word for it. Same test file. This time: real vulnerabilities, correctly flagged, nothing made up. Point it at clean code afterward and it correctly said nothing was wrong, which honestly felt like a bigger win than finding the bugs did. The annoying lesson I wanted this project to feel impressive. More agents, more debate, more "look how sophisticated this is." What actually worked was the boring answer: fewer agents, clear roles, one checking the other's work instead of everyone talking at once. I named the final version Synod

2026-07-05 原文 →
AI 资讯

purefetch: a fastfetch-style system info tool in Rust with zero dependencies

I like neofetch / fastfetch , but I wanted one with a genuinely empty dependency graph — nothing pulled from crates.io. So I built purefetch : a small system-info fetcher written entirely in Rust using only std plus raw Linux syscalls. Disclosure up front: purefetch was built largely with AI assistance (Claude Code). I directed the design, and every change was reviewed and tested — including running it on four architectures under QEMU — but most of the code is AI-generated. I'd rather be honest about that than pretend otherwise. _,met$$$$$gg. ooonea@unicorn ,g$$$$$$$$$$$$$$$P. ────────────── ,g$$P" """Y$$.". OS Debian GNU/Linux 13.5 (trixie) x86_64 ,$$P' `$$$. Host ThinkPad P53 (20QQS0JD01) ',$$P ,ggs. `$$b: Kernel 6.12.94+deb13-amd64 `d$$' ,$P"' . $$$ Uptime 6 days, 15 hours, 30 mins $$P d$' , $$P Packages 2477 (dpkg), 1 (flatpak) $$: $$. - ,d$$' Shell zsh 5.9 $$; Y$b._ _,d$P' Display 1920x1080 (eDP-1) Y$$. `.`"Y$$$$P"' DE GNOME 48.7 `$$b "-.__ WM Mutter (Wayland) `Y$$ Terminal kitty 0.41.1 `Y$$. CPU Intel(R) Core(TM) i7-9850H @ 4.60 GHz `$$b. GPU Quadro RTX 3000 `Y$$b. Memory 15.28 GiB / 62.61 GiB (24%) `"Y$b._ Swap 0 B / 8.00 GiB (0%) `""" Disk (/) 8.52 GiB / 489.57 GiB (2%) Locale en_US.UTF-8 Battery 76% (Not charging) Zero dependencies, really No libc crate, no sysinfo , no nix , no color crate — nothing from crates.io. Almost everything is just reading and parsing /proc and /sys . The result is a single ~484 KiB binary that builds offline. The only things std can't do are statfs (disk usage) and ioctl (terminal size / tty check). Instead of pulling in a binding crate, those are issued as raw Linux syscalls via core::arch::asm! : #[cfg(target_arch = "x86_64" )] unsafe fn syscall3 ( n : usize , a1 : usize , a2 : usize , a3 : usize ) -> isize { let ret : isize ; core :: arch :: asm! ( "syscall" , inlateout ( "rax" ) n as isize => ret , in ( "rdi" ) a1 , in ( "rsi" ) a2 , in ( "rdx" ) a3 , out ( "rcx" ) _ , out ( "r11" ) _ , options ( nostack ), ); ret } Four arch

2026-07-04 原文 →
AI 资讯

Subtraction > Addition: Why the Best Meditation App Asks Nothing From You

Every meditation app I have tried wants something from me. Headspace wants me to maintain a streak. Calm wants me to listen to a Daily Jay. Insight Timer wants me to join a group. One after another, apps designed to reduce my stress started creating new forms of it. The Feature Trap Here is what happened to meditation apps between 2015 and 2026: 2015: "Just meditate 10 minutes a day." 2018: "Track your streak! You do not want to break it, do you?" 2021: "Compare your stats with friends. See who meditated more this week." 2024: "AI-generated personalized guided meditation based on your emotional state, delivered at the optimal time based on your circadian rhythm." Wait — was not the whole point to stop optimizing everything? Subtraction as a Feature I switched to OneZen last month. Here is what I noticed: No onboarding. Open the app. Breathe. Close the app. That is the entire user flow. No streaks. I missed three days last week and the app did not shame me. It did not even notice. It just opened to the same calm screen, waiting, as if three days was the same as three hours. No gamification. No XP points. No badges. No "you are in the top 14% of meditators this month." Because meditation is not a competition you can win. What Subtraction Feels Like The first week was uncomfortable. I kept checking if I had "done it right." There was nothing to check. No dashboard. No stats. Just me and my breath. By week two, something shifted. Meditation stopped being a task on my to-do list and started being... just breathing. I was not practicing to maintain a number. I was practicing because it felt good. This is what minimalism actually means. Not fewer pixels. Less cognitive load. Less obligation disguised as features. The Bigger Idea OneZen's philosophy applies far beyond meditation apps: The best productivity tool is the one with the fewest notifications. The best social network is the one that respects when you leave. The best habit tracker does not exist — because the ha

2026-07-04 原文 →
产品设计

Como o kernel impede que processos executem instruções arbitrárias de CPU?

A gente sempre ouve falar que o sistema operacional impede que um processo veja a memória do outro ou que o programa fale diretamente com o hardware, mas normalmente não explicam o "como". Eu sempre achei isso meio mágico até que eu resolvi ir atrás da resposta, e é bem interessante. Vou me basear na arquitetura x86, mas é provável que outras arquiteturas sejam parecidas. O problema: a CPU Pra CPU não existe processo, kernel, sistema operacional. Existe só endereços de memória de onde ela lê a próxima instrução e executa. Se a CPU pode falar direto com a RAM, SSD, teclado, mouse, tela... O que me impede de escrever um programa pra ler suas senhas e tokens direto da RAM? Ou de ler arquivos e alterar arquivos sensíveis direto no SSD? Por outro lado, se o kernel fiscalizasse cada instrução que da CPU antes dela executar, isso seria extremamente lento... Outro problema: os interrupts Se a CPU só executasse sequencialmente, seu sistema poderia executar várias coisas e esquecer de checar se uma tecla foi apertada, se o mouse mexeu, etc... Então certos eventos interrompem o que quer que a CPU esteja fazendo para serem tratados assim que possível. Alguns exemplos de interrupt são: Teclas do teclado pressionadas ou soltas Botões e movimento do mouse Timers Operações de disco assíncronas Pacotes de rede recebidos/transmitidos Uma solução: rings Os processadores da arquitetura x86 tem o esquema de rings. Pense em rings como grau de limitação. Ring 0 significa limitação zero, ou seja, acesso a todas as instruções da CPU e consequentemente acesso total ao hardware e memória. O kernel roda em ring 0, ou kernel mode. O kernel assim que é carregado configura todos os interrupts handlers da CPU para executar o handler apropriado do kernel, em kernel mode, claro. Em ring 3 a CPU fica limitada e não pode fazer instruções consideradas privilegiadas. E obviamente em ring 3 a CPU não consegue se colocar em ring 0 sozinha, pois dessa forma qualquer programa conseguiria se pôr em ring 0. O

2026-07-04 原文 →
AI 资讯

Dev log #9 Hardening Kademlia DHT and automating the Neovim grind

Seven days of flow. Fixed a peer identity binding issue in py-libp2p, automated my Neovim lockfile merges, and added a massive batch of notes on xv6 and Category Theory. 10 commits and a solid PR in the works. TL;DR I managed to hit a perfect seven-day streak this week, balancing some deep-dive p2p networking work with necessary maintenance on my local environment. The highlight was opening a PR in py-libp2p to tighten up how PeerRecords are handled in the Kademlia DHT. On the side, I spent time automating the annoying parts of my Neovim config and dumping a fresh batch of notes into my knowledge base. 10 commits, 204 lines added, and a much cleaner workflow to show for it. What I Built Neovim Configuration & CI I’m a firm believer that your editor should work for you, not the other way around. My nvim repo saw a lot of action this week—9 commits in total—but most of it was under-the-hood maintenance. I’ve been leaning on Lua to keep things snappy, and this week was about ensuring my plugin ecosystem doesn't rot. I pushed several updates to keep plugins at their latest versions, but the real "quality of life" improvement was adding a chore to auto-resolve lazy-lock.json merge conflicts. If you’ve ever worked on your Neovim config across multiple machines, you know the headache of the lockfile drifting. I set up a flow to prioritize incoming changes, which saves me from manually triaging JSON diffs every time I pull from dev . It’s a small tweak, but it removes a recurring friction point in my daily flow. I also spent time cleaning up the root of the config, with about 37 additions and 33 deletions—refactoring is a constant process when you live in your terminal. The Knowledge Base I also put some serious time into main-notes . I’m currently going deep on a few different subjects, and I use this repo as my "second brain." I added 167 lines of new material across 13 files, covering a pretty diverse range of topics: xv6 (the re-implementation of Unix V6), Category Theo

2026-07-03 原文 →
AI 资讯

I Spent 40 Minutes at 11pm Debugging a Deploy That Wasn't Broken

I once spent forty minutes at eleven at night debugging a deploy that wasn't broken. The release script ran the database migration, the migration threw connection refused , the script exited non-zero, the deploy rolled itself back, and I got paged. So I did the things you do. I read the migration. I read the logs. I checked the database — it was up, it was healthy, it accepted my connection instantly. I re-ran the deploy and it worked. I chalked it up to gremlins and went to bed, which is the part I'm not proud of, because it happened again two days later. That time I watched the timing: the script brought up a fresh database container and started the migration about six seconds before Postgres finished initializing and began accepting connections. The migration was racing the database's boot. Most of the time it won. The times it lost, I lost forty minutes. The script wasn't wrong about anything except one assumption: that a dependency is ready the instant you ask for it. In production, dependencies are eventually ready That's the mental model shift. Networks blip. A service you call returns a 503 for the two seconds it takes to finish a rolling restart. An API rate-limits you with a 429 it fully expects you to retry. A fresh container's database isn't accepting connections for its first few seconds. Treating the first failure as fatal turns every one of these normal, transient conditions into a paged engineer — and the script that handles them isn't smarter — it declines to give up on the first try. But retrying naively is its own trap. Retry instantly and you hammer a recovering service into staying down. Retry forever and a genuinely dead dependency hangs your script indefinitely. Retry a 404 and you wait a minute to confirm what you already knew. Good retries are bounded, backed off, and selective. A retry function you can reuse anywhere #!/bin/bash # Purpose: survive transient failures instead of dying on the first error set -euo pipefail CHECK = "✓" CROSS = "

2026-07-02 原文 →
AI 资讯

What Feature Makes You Leave a Resume Builder Website?

I'm curious... What's the one feature that instantly makes you stop using a resume builder? For me, it was simple: You spend time creating your resume, everything looks great, and then the site asks you to pay just to download it. That experience inspired me to build Resumship, a resume builder where downloading your resume is completely free. Now I'm thinking about the next features to add, and I'd love to hear from the community. If you were building the ideal resume builder, what features would you include? AI-powered resume suggestions? Better ATS optimization? More templates? Portfolio integration? Cover letter generation? Something completely different? If you have a minute, I'd also love for you to try Resumship and share your honest feedback. 🌐 https://resumship.com Your feedback will directly influence what gets built next. Every suggestion, bug report, or feature request helps make the platform better for everyone. Looking forward to hearing your ideas! 🚀

2026-07-01 原文 →
AI 资讯

From one blocking accept() to epoll: a C TCP server up the I/O ladder, measured

I connected one client to a blocking TCP server and held the socket open without sending a single byte. Then I connected a second client and sent it a line of text. The second client sat there for 1.51 seconds with no reply. It got its echo back one millisecond after I closed the first connection. That 1.51 seconds is the reason the other six versions of this server exist. Last week I wrote up why I rebuilt this server seven times : framework knowledge resets every few years, the layer underneath it compounds. That piece stayed at the level of outcomes. This one goes the other way, down into the code and the numbers. The claims that matter here are the kind you can read a hundred times without being able to derive them. "select is O(n)." "epoll only hands you the ready fds." I had read both for years. I wanted to make my own machine say them out loud. The target the whole exercise is built around is Dan Kegel's old C10K problem : how do you serve ten thousand clients at once on one server? Each of the seven versions hits a wall, and the wall is what names the next one. The whole thing is one echo server written seven times, no libraries beyond libc, on GitHub . Every number below is from running it on macOS (Apple clang 21, darwin 25.4) on 2026-06-29. The binaries are built with AddressSanitizer and UBSan on, so read the absolute microseconds loosely. The structure is what holds. Phase 01: blocking, and the 1.5 second stall The first server is the one everybody writes first. Accept a connection, talk to it, close it, accept the next. for (;;) { int client_fd = accept ( server_fd , NULL , NULL ); if ( client_fd == - 1 ) { perror ( "accept" ); continue ; } handle_client ( client_fd ); close ( client_fd ); } handle_client loops on read until the client hangs up. Both accept and read block: when there is nothing to do, the thread sleeps in the kernel. That is good for idle cost and fatal for everything else. While the server is parked in read waiting on client A, client

2026-06-30 原文 →
AI 资讯

Linux Logs Explained Simply

When something breaks in Linux, experienced engineers don’t guess. They check the logs. 👉 Logs are the “black box recorder” of a Linux system. They tell you: what happened when it happened why it failed If you can read logs properly, you can debug almost anything. What Are Logs? Logs are records of system and application activity. Linux constantly records: System events Errors User activity Application behavior Linux constantly records: Where are Logs Stored? Most Linux logs are stored inside: /var/log Check logs directory: cd /var/log ls This is the first place DevOps engineers check during system issues. Important Log Files Log File Purpose Command to View /var/log/syslog General system messages tail /var/log/syslog /var/log/auth.log Login attempts & authentication tail /var/log/auth.log /var/log/kern.log Kernel & hardware messages dmesg or tail /var/log/kern.log /var/log/nginx/error.log Web server errors (Nginx) tail /var/log/nginx/error.log /var/log/dmesg Boot and hardware logs dmesg /var/log/apache2/ -> Apache logs These logs help you identify system, security, and application-level issues. View Logs Using cat cat /var/log/syslog Good for small files. Using less less /var/log/syslog Useful keys:: Space → Next page b → Previous page q → Quit 👉 Best for large log files. Using tail tail /var/log/syslog Show last 10 lines. Real-Time Monitoring (tail -f) tail -f /var/log/syslog 👉 -f = follow live updates This is one of the most-used debugging commands in production servers. Stop with: Ctrl + C Searching Logs with grep grep error /var/log/syslog Case-insensitive: grep -i failed /var/log/auth.log Show latest matching errors: grep error /var/log/syslog | tail -n 50 👉 Essential for filtering huge logs quickly. Boot & Hardware Logs (dmesg) dmesg Shows: Boot messages Hardware detection Kernel events Useful for startup and hardware troubleshooting. Modern Log System: journalctl Modern Linux systems use systemd logs . journalctl Recent errors: journalctl -xe Specific servic

2026-06-30 原文 →
AI 资讯

Install NixOS on Jetorbit

Overview Tulisan ini menceritakan pengalaman saya meng-install NixOS di VPS Jetorbit memakai nixos-anywhere , dideploy dari laptop macOS (nix-darwin). Komposisi Laptop (macOS + nix-darwin) : Semua konfigurasi NixOS dibuat di sini, lalu dikirim ke server. VPS Jetorbit (x86_64 Linux) : target deploy. Boot lewat legacy BIOS , dengan IP statis (bukan DHCP). nixos-anywhere : dipakai sekali saja untuk install awal. nixos-rebuild : dipakai untuk update konfigurasi setelah install awal. Catatan Penting : VPS tidak perlu menyimpan file konfigurasi sendiri. Kita edit config di laptop, lalu push ke VPS lewat SSH. Tidak ada apt update , tidak ada config drift, dan kondisi server selalu reproducible dari git. Pre-flight: Cek Sebelum Menyentuh Server Banyak kegagalan install sebenarnya bisa dicegah kalau kita cek tiga hal ini: 1. Mode boot: UEFI atau legacy BIOS? Ini menentukan konfigurasi bootloader. Salah konfigurasi di sini dapat menyebabkan GRUB gagal saan install nanti. Di VPS (SSH ke VPS): [ -d /sys/firmware/efi ] && echo "UEFI" || echo "BIOS" Di Jetorbit secara default adalah BIOS . Artinya konfigurasi GRUB mode legacy BIOS, bukan EFI. 2. Networking: IP, netmask, dan gateway Jetorbit memakai IP statis, bukan DHCP. Kalau konfigurasi NixOS kita set IP maka NixOS akan fallback ke DHCP, dan akan gagal dapat IP, sehingga server jadi tidak bisa diakses sama sekali setelah reboot. Di VPS: ip -4 a # lihat IP + CIDR dan nama interface (misal. ens3) ip route # lihat "default via X.X.X.X", itu gateway-nya Contoh: 2: ens3: ... inet 110.XXX.XXX.XXX/24 brd 110.XXX.XXX.255 scope global ens3 3. SSH Root nixos-anywhere memerlukan akses root ke server untuk bisa melakukan instalasi. Akses ini didapat lewat SSH key, bukan password. Jadi pastikan Di VPS: public key sudah terdaftar di root . Konfigurasi SSH root ini bisa dilakukan saat install OS awal di panel Jetorbit atau dikonfigurasi secara manual di ~/.ssh/authorized_keys . Cara Kerja nixos-anywhere Sebelum menjalankan perintahnya, ada ba

2026-06-29 原文 →
AI 资讯

Why am I building a DevOps Infrastructure Lab?

I am committed to understand how systems actually work. I'm working on a multi-node lab to follow the complete path of a request from Python APIs to Linux processes, through Docker containers, networking and observability. The idea is simple: build a system that observes another system to understand the abstraction layers behind modern infrastructure. This project is about learning by building, experimenting and understanding what happens under the hood. Link: [ https://github.com/daniloprandi/devops-network-automation-lab ] DevOps #Linux #Python #Docker #Networking #Observability #Infrastructure

2026-06-29 原文 →
AI 资讯

TeamLab 那片會跟著你走的花海,原理拆解 DIY

TeamLab 那片會跟著你走的花海,原理拆解+DIY 先看這張圖 這是 TeamLab 在東京台場的《呼應燈之森林》。當你走過去,附近的燈會慢慢亮起;你離開後,燈又慢慢暗下去,像是真的森林一樣。 還有另一個作品《花與人的共存》,花叢會跟著你移動——你站的地方,花就開在你腳邊;你離開,花就凋謝。 這兩件作品的核心邏輯是一樣的。這篇文章就來拆解它。 原理一:偵測位置 TeamLab 的互動裝置需要知道「你在哪裡」。 最常見的方法有兩種: 紅外線感應 :在地面下方埋紅外線接收器,你走過時阻擋光線,系統就知道有人在這個位置。缺點是只能測「有沒有人」,不能測「人在哪一個方向」。 深度相機(RealSense / Kinect) :像 Xbox 的體感相機,透過紅外線測量每一個點到你相機的距離,生成一張「深度地圖」。軟體在深度地圖裡找出人體的位置,然後算出座標。 DIY 版本 :一塊 Arduino + 超音波感測器(HC-SR04,大約 60 元)就能做到基本的「有人靠近」偵測。 原理二:控制回應 知道你在哪裡之後,系統要決定「要做什麼回應」。 TeamLab 的做法是 :不是「觸發」,而是「強度變化」 。 傳統的感應燈:感應到人 → 燈全亮 → 人離開 → 燈全滅。 TeamLab 的邏輯:感應到人 → 燈慢慢變亮(0.5 秒)→ 人持續在 → 維持亮度 → 人離開 → 慢慢變暗(2 秒)。 「慢慢」是關鍵。瞬間變化讓人注意到「科技」;緩慢變化讓人以為「這個空間有生命」。 這就是「驚奇設計」的核心: 時機對了,物理反應看起來像生物反應。 原理三:集體行為 最後一個秘密:TeamLab 的裝置很少只有一個「回應」。 通常會有 100-500 個元素(燈、花、光點)。每個元素各自計算自己與你的距離,決定自己的亮度或顏色。 當 500 個燈各自以稍微不同的速度亮起和暗下,你看到的不是「一個燈亮了」,而是「一片森林在你腳下呼吸」。 心理錯覺 :你把「一群各自輕微不同步的簡單反應」,詮釋成「一個整體有意志的生物」。 用 Arduino 自己做一個迷你版 材料: Arduino Uno(大約 200 元) 超音波感測器 HC-SR04(大約 60 元) LED 燈 x 3(大約 15 元) 麵包板和杜邦線 原理很簡單: 超音波感測器偵測距離 距離越近,LED 越亮(用 PWM 訊號控制) 距離越遠,LED 越暗 int trig = 7 ; int echo = 6 ; int led = 9 ; void setup () { Serial . begin ( 9600 ); pinMode ( trig , OUTPUT ); pinMode ( echo , INPUT ); pinMode ( led , OUTPUT ); } void loop () { digitalWrite ( trig , LOW ); delayMicroseconds ( 2 ); digitalWrite ( trig , HIGH ); delayMicroseconds ( 10 ); digitalWrite ( trig , LOW ); long duration = pulseIn ( echo , HIGH ); long distance = duration * 0.034 / 2 ; // 距離越近,LED 越亮 int brightness = map ( distance , 0 , 100 , 255 , 0 ); brightness = constrain ( brightness , 0 , 255 ); analogWrite ( led , brightness ); delay ( 50 ); } 這不是 TeamLab,但這是你自己做的「會呼吸的燈」。每個 maker 都是從這裡開始的。 庭庭:這個看起來很難 真的沒有你想的那麼難。 需要的東西全部可以在蝦皮買到,全部加起來大約 300 元。網路上有超多 Arduino 教學,關鍵字搜「Arduino 超音波 LED」就有幾十篇中文教學。 你不需要懂電子,只需要跟著步驟做,做完會有「哇,我自己做出了一個會亮的東西」的感動。 如果你想更進一步 TeamLab 的進入門檻其實不是技術,是「你要把技術藏在美學後面」。 推薦兩個方向可以繼續研究: p5.js + webcam :用 p5.js 讀取你的 webcam 影像,偵測顏色或移動。相當於用軟體做到 Kinect 的效果,零硬體成本。 Processing + 投影機 :把電腦畫面投射到牆上或地面上,加上感測器,就是一個簡單版互動投影。投影機在蝦皮一兩千元就有。 今日概念 :TeamLab 的魔法不是魔法,是三個原

2026-06-28 原文 →