Skip to content

Archive / page 65

All articles

Every practical article from the Nalar archive, newest first.

Go 07 Sep 2026 8 min read

Handle Buffered Write Errors Correctly in Go

Buffering output can reduce write overhead, but it also changes when an I/O failure becomes visible. With an unbuffered writer, a call to Write normally reaches the underlying destination immediately. With bufio.Writer, a successful call may only mean that the bytes were accepted into memory. The actual write to a file, socket, pipe, or other destination can happen later, often during Flush. That distinction creates a common production bug: code checks every apparent write, defers Flush, and still returns success after the final flush fails.

Artificial Intelligence 07 Sep 2026 12 min read

Gradient Noise Scale and Batch Size

Increasing a neural network’s batch size can make more accelerators useful, but the benefit does not grow indefinitely. At some point, processing more examples before each update gives a cleaner estimate of nearly the same gradient direction while consuming additional examples and compute. Gradient noise scale provides a useful mental model for this transition. It compares the variation in per-example gradients with the strength of their average. When gradient estimates are noisy relative to their mean, averaging more examples can remove meaningful noise. When they are already stable, a larger batch has less statistical work left to do.

Artificial Intelligence 07 Sep 2026 9 min read

Gradient Centralization in Neural Network Training

Neural network optimizers normally consume the gradients produced by backpropagation directly. Gradient centralization inserts one small transformation between those two steps: for selected weight tensors, it subtracts the mean of each gradient vector before the optimizer uses it. That operation is easy to implement, but its effect is easy to misunderstand. It is not gradient clipping, because it does not cap large values. It is not normalization, because it does not divide by a norm or standard deviation. It changes the direction of the update by removing one particular component.

Cybersecurity 07 Sep 2026 9 min read

Fail Closed When Authorization Dependencies Are Unavailable

An application may have a correct authorization policy and still expose protected actions when the system that evaluates that policy is unavailable. The dangerous shortcut is to treat a timeout, network error, or missing policy result as permission so that the application can keep working. That changes an availability problem into an access-control problem. A temporary dependency failure can then let a requester perform an action that the application never established they were allowed to perform.

Software Engineering 07 Sep 2026 9 min read

Evolving Data Shapes with Expand and Contract

A data change can look trivial in code and still be dangerous in a running system. Renaming a field, splitting one value into two, or changing a message shape may require several application versions, background jobs, and consumers to coexist while the change is in progress. The risky assumption is that the whole system changes at once. In practice, deployments take time, workers may finish old jobs after new code is live, and independently deployed consumers may upgrade later. If one release removes the old shape while something still depends on it, a locally correct change becomes a system failure.

Cybersecurity 07 Sep 2026 10 min read

Do Not Use Personal Questions for Account Recovery

A login flow can use strong passwords and multi-factor authentication, yet the account can still be easier to take over through its recovery path. If a user who cannot sign in only needs to answer questions such as a birth city, school name, or family detail, the recovery process may accept evidence that another person can discover, infer, or repeatedly guess. That makes personal security questions a poor substitute for authentication. The problem is not merely that some questions are badly chosen. The deeper problem is that facts about a person are usually not secrets designed for authentication: they can be shared, become public, remain unchanged for years, and be known by people other than the account owner.

Cybersecurity 07 Sep 2026 7 min read

Do Not Silently Downgrade Authentication

A login system may support several ways to prove identity. That flexibility becomes dangerous when the system silently replaces a required authentication method with a weaker one because the preferred method is unavailable. Imagine an administrative account that normally requires a password plus a phishing-resistant authenticator. The authenticator service has a temporary outage. If the application responds by accepting only the password, an availability problem has changed the account’s security requirement. An attacker who has the password now needs less proof precisely while a security dependency is failing.

Artificial Intelligence 07 Sep 2026 11 min read

Diversify RAG Retrieval with Maximal Marginal Relevance

A retrieval-augmented generation (RAG) system can retrieve highly relevant passages and still build a poor context. The problem appears when the top results repeat the same fact in slightly different wording. Suppose five retrieved chunks all explain how to reset an API token, while a lower-ranked chunk explains the permission change that must happen afterward. Filling the context window with the five near-duplicates gives the language model less useful evidence than selecting a smaller set that covers both parts of the task.

Artificial Intelligence 07 Sep 2026 11 min read

Diagnose Hubness in Embedding Retrieval

Embedding retrieval is usually explained one query at a time: encode the query, compare it with stored vectors, and return the nearest items. That view can hide a collection-level failure mode. A document may look reasonably similar to many unrelated queries and therefore appear in far more result lists than it should. Such an item is called a hub. The broader phenomenon, hubness, is a tendency for some points in a vector space to become nearest neighbors of unusually many other points. It matters because a retriever can have healthy-looking similarity scores while repeatedly wasting top positions on generic or geometrically favored items.

Artificial Intelligence 07 Sep 2026 10 min read

Diagnose and Prevent Dead ReLU Neurons

ReLU is a simple and effective activation function, but its simplicity creates a failure mode that is easy to miss. A neuron can reach a state where its pre-activation is negative for every relevant input. Its ReLU output is then always zero, and the gradient through that activation is also zero. If this persists, the neuron may stop participating in learning. This is commonly called a dead ReLU or dying ReLU problem. It does not mean that every zero activation is a defect: sparse activations are a normal consequence of ReLU. The useful question is whether a unit is inactive only for some inputs or effectively inactive across the data it needs to model.

Software Engineering 07 Sep 2026 9 min read

Designing Strict Input Contracts

Being tolerant of imperfect input can look helpful. A parser silently fixes an invalid value, an API treats an unknown option as a default, or a service accepts several spellings for the same field. The immediate caller succeeds instead of receiving an error. The cost often appears later. Once clients discover that invalid input is accepted, they may depend on that behavior. Tightening validation then becomes a compatibility change, and different implementations may interpret the same malformed input differently.

Software Engineering 07 Sep 2026 10 min read

Designing APIs for Observable Behavior

An API can keep every documented promise and still break its users. Suppose a function returns search results with no documented ordering guarantee. Its current implementation happens to return items alphabetically. A client notices that behavior and removes its own sorting step. Months later, the implementation changes and returns the same items in a different order. The API still satisfies its written contract, but the client breaks. This is the practical problem behind Hyrum’s Law: when an API has enough consumers, some consumers are likely to depend on almost any observable behavior, whether or not that behavior was intended as part of the contract.

Cybersecurity 07 Sep 2026 9 min read

Design Recovery Codes as One-Time Authenticators

Multi-factor authentication can protect an account well during normal login and still leave a weak path around that protection. The weak path is often recovery: a user loses a device, reaches for a saved recovery code, and the application accepts that code as proof of account control. A recovery code is therefore not merely a convenience string. While it is valid, it is an authenticator. If someone else obtains it, they may be able to use the same recovery path as the legitimate user.

Artificial Intelligence 07 Sep 2026 9 min read

Defer Uncertain Classifier Predictions with Selective Classification

A classifier does not have to make an automated decision for every input. In many systems, forcing a prediction on the hardest cases is exactly what creates expensive mistakes. Imagine a model that routes customer support messages. Clear password-reset requests can be handled automatically, while ambiguous messages could be sent to a human queue. The important design question is no longer only “How accurate is the classifier?” It is also “How accurate is it on the cases we allow it to handle?”

Python 07 Sep 2026 11 min read

Create and Clean Up Temporary Files Safely in Python

Temporary files appear in more programs than their name suggests. A command-line tool may need scratch space while transforming a large file. A test may need an isolated directory. A program may need to hand a real filesystem path to another process and remove it afterward. The risky part is not writing the bytes. It is choosing a name, creating the file without a race, deciding who owns cleanup, and handling differences between a file object and a filesystem path.

Artificial Intelligence 07 Sep 2026 11 min read

Compress Neural Network Layers with Low-Rank Factorization

Large neural networks spend much of their memory and computation multiplying activations by weight matrices. Some of those matrices contain more independent structure than the model actually needs for a particular deployment. If so, we can approximate one large matrix with two smaller matrices and reduce the number of stored parameters and multiply-add operations. This technique is called low-rank factorization. The central idea is simple, but using it well requires more than choosing a smaller number. Compression changes the weights, approximation error can accumulate through a network, and fewer arithmetic operations do not guarantee lower wall-clock latency on every device.

Go 07 Sep 2026 12 min read

Compose Sequential Streams in Go with io.MultiReader

Programs often need to present several pieces of data as one input stream. A request body may need a generated header followed by a file. A test may need a prefix, a fixture, and a suffix. A protocol adapter may need to expose several existing readers through an API that accepts only one io.Reader. The obvious solution is to read every piece into memory, concatenate the byte slices, and create a new reader over the result. That is reasonable for small, already-buffered data. It is a poor fit when one source is large, slow, or naturally streaming because the consumer cannot start until the combined buffer has been built.

Cybersecurity 07 Sep 2026 9 min read

Compare Secret Values Without Timing Leaks

Applications compare security-sensitive values constantly: message authentication codes, webhook signatures, API tokens, recovery codes, and other secret authenticators. A normal string or byte comparison may stop as soon as it finds a mismatch. That is efficient, but when the compared value is secret, the amount of work can depend on how much of the candidate matched. If an attacker can obtain useful timing measurements over many attempts, data-dependent comparison time can become an information leak. The practical defense is not to write a clever comparison loop. Use a well-reviewed constant-time comparison primitive provided by the language, cryptographic library, or platform for secret values of the expected form.

Go 07 Sep 2026 7 min read

Combine Independent Failures in Go with errors.Join

A function sometimes performs several independent operations and more than one can fail. Cleanup is a common example: closing one resource should not prevent the program from attempting to close the next. Validation can have the same shape when callers benefit from seeing several independent problems at once. Returning only the last error loses information. Returning only the first error may hide failures that happened later. Go’s errors.Join provides a standard way to return one error value that still wraps multiple underlying errors.

Software Engineering 07 Sep 2026 11 min read

Circuit Breakers for Failing Dependencies

A dependency can fail in a way that is worse than an immediate error. It may accept connections but respond slowly, time out repeatedly, or reject nearly every request while callers continue sending more work. If your application keeps calling that dependency for every incoming request, the original failure can consume connection pools, worker capacity, and latency budgets in your own service. Retrying every failure can increase the pressure further.

Artificial Intelligence 07 Sep 2026 11 min read

Chunking Documents for RAG Without Losing Context

A retrieval-augmented generation (RAG) system can have a strong embedding model and still retrieve poor evidence. One common reason is document chunking: the text was divided into units that are awkward to search or incomplete when read on their own. If chunks are too large, one embedding must represent several unrelated ideas and retrieval becomes less precise. If chunks are too small, the retrieved text may omit the definitions, qualifiers, or surrounding steps needed to answer correctly. The problem is therefore not to find one universally correct chunk size. It is to create retrieval units that are focused enough to match a query and complete enough to be useful after retrieval.

Python 07 Sep 2026 8 min read

Build Reliable Worker Queues in Python with queue.Queue

A worker thread is easy to start. A reliable worker queue is harder. The difficult parts appear when production code must answer questions such as: What happens when producers are faster than consumers? How does the main thread know that processing, rather than merely dequeuing, is complete? How do workers stop without abandoning queued work? What happens if processing raises an exception? Python’s queue.Queue provides the synchronization needed to pass work safely between threads, but correct coordination still depends on a few application-level invariants. The most important are to bound work when memory matters, pair every successful get() with exactly one task_done(), and separate “all work is finished” from “workers should exit.”

Python 07 Sep 2026 11 min read

Bound In-Flight Thread Pool Work in Python

A thread pool limits how many functions run at the same time, but it does not automatically limit how much work your producer can queue. That distinction matters when the input is large or unbounded. A loop can submit millions of tasks to a ThreadPoolExecutor while only a handful of worker threads execute them. The remaining tasks are pending Future objects, along with their arguments and other referenced state. If the producer is much faster than the workers, memory use can grow long before CPU or network capacity is exhausted.

Cybersecurity 07 Sep 2026 9 min read

Bind Invitations to the Intended Recipient

An invitation link often looks like a simple onboarding convenience: an administrator enters an email address, the application sends a link, and the recipient joins a workspace or project. But accepting that invitation creates authorization. If the application checks only that the link contains a valid token, whoever presents the token may receive the membership. That distinction matters when invitation messages are forwarded, opened in a shared mailbox, exposed through another system, or clicked while the browser is signed in to a different account. A strong random token can prove that someone possesses the invitation link. By itself, it does not prove that the signed-in account is the person the inviter intended to authorize.