npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

tofu-log

v0.1.4

Published

A developer debugging overlay for React Native Expo apps

Readme

🪐 TofuLog

A lightweight developer debugging overlay for React Native Expo apps with a polished terminal-inspired experience. Inspect logs, network requests, crashes, and device info directly on your device with beautiful terminal-style output.

Features

Vibe Logger - Terminal-Style Console Output

  • High-contrast terminal styling with teal accents and monospace fonts
  • Smart filtering - Only warnings/errors show in Metro terminal by default (keeps it clean!)
  • Full log history - Everything is captured in the beautiful in-app overlay
  • Push to Terminal - Manually send any log to Metro with one tap
  • Configurable - Override terminal log level if you want to see everything

Smart Log Viewer

  • Terminal-style UI with ASCII rendering
  • Filter by level - log, info, warn, error, debug
  • Search logs - Find what you need fast
  • Copy on long-press - Share logs with your team
  • Data preview - See object/array contents inline

AI-Ready Debugging

  • Copy for AI - One-click formatted context for ChatGPT/Claude
  • Share reports - Export crash reports and network requests
  • Copy as cURL - Replay network requests outside the app

Network Inspector

  • Monitor all fetch/XHR requests with headers, bodies, and timing
  • Copy requests as cURL commands
  • View request/response bodies with syntax highlighting

Crash Reporter

  • Automatic error boundary with stack traces and component trees
  • Share crash reports for debugging
  • Copy formatted errors for AI assistance

Device Info

  • View device, OS, app, and runtime information
  • Helpful for debugging device-specific issues

Beautiful UX

  • Saturn FAB - Draggable floating action button with teal glow
  • Shake to Open - Shake your device to toggle the debug panel
  • Dark theme - Purpose-built for late-night debugging sessions
  • Zero Config - Works out of the box, auto-disabled in production

Installation

npm install tofu-log
# or
yarn add tofu-log

Peer Dependencies

This package requires the following Expo packages:

npx expo install @expo/vector-icons expo-sensors expo-device expo-constants expo-clipboard expo-file-system expo-sharing

Quick Start

Wrap your app with the DevOverlay component:

import { DevOverlay } from 'tofu-log';

export default function App() {
  return (
    <DevOverlay>
      <YourApp />
    </DevOverlay>
  );
}

That's it! The overlay is automatically enabled in development (__DEV__) and disabled in production.

Usage

Opening the Overlay

  • Tap the FAB — A floating Saturn button appears on screen (draggable!)
  • Shake your device — Shake gesture toggles the overlay

Tabs

| Tab | Description | |-----|-------------| | Logs | Terminal-style log viewer with search, filtering, and push-to-terminal | | Network | Inspect requests with Copy as cURL and detailed headers/bodies | | Crashes | Error reports with Copy for AI and Share functionality | | Device | Device model, OS version, app info, and runtime details |

Configuration

import { DevOverlay, setTerminalLogLevel } from 'tofu-log';

// Basic usage
<DevOverlay
  enabled={true}           // Override __DEV__ check
  config={{
    shakeToOpen: true,     // Enable shake gesture (default: true)
    showFab: true,         // Show floating action button (default: true)
    maxLogs: 500,          // Maximum logs to store (default: 500)
    maxNetworkRequests: 100, // Maximum network requests to store (default: 100)
  }}
>
  <YourApp />
</DevOverlay>

// Customize terminal log level (optional)
setTerminalLogLevel('all');  // Show all logs in Metro terminal
setTerminalLogLevel('warn'); // Only warn/error (default - keeps terminal clean!)
setTerminalLogLevel('error'); // Only errors

API Reference

Components

<DevOverlay>

Main wrapper component that provides the debug overlay.

| Prop | Type | Default | Description | |------|------|---------|-------------| | children | ReactNode | required | Your app content | | enabled | boolean | __DEV__ | Force enable/disable the overlay | | config | DevOverlayConfig | {} | Configuration options |

<ErrorBoundary>

Standalone error boundary component (also built into DevOverlay).

import { ErrorBoundary } from 'tofu-log';

<ErrorBoundary
  onError={(report) => console.log(report)}
  fallback={<CustomErrorScreen />}
>
  <YourComponent />
</ErrorBoundary>

Hooks

useDevOverlay()

Access the overlay state and controls programmatically.

import { useDevOverlay } from 'tofu-log';

function MyComponent() {
  const {
    show,           // () => void - Open overlay
    hide,           // () => void - Close overlay
    toggle,         // () => void - Toggle overlay
    isVisible,      // boolean - Current visibility
    logs,           // LogEntry[] - Captured logs
    networkRequests, // NetworkRequest[] - Captured requests
    crashReports,   // CrashReport[] - Captured crashes
    clearLogs,      // () => void - Clear all logs
    clearNetworkRequests, // () => void - Clear network requests
    clearCrashReports,    // () => void - Clear crash reports
  } = useDevOverlay();

  return <Button onPress={toggle} title="Toggle Debug" />;
}

Types

type LogLevel = 'log' | 'warn' | 'error' | 'info' | 'debug';

interface LogEntry {
  id: string;
  level: LogLevel;
  message: string;
  timestamp: number;
  data?: unknown[];
}

interface NetworkRequest {
  id: string;
  method: string;
  url: string;
  status?: number;
  statusText?: string;
  requestHeaders?: Record<string, string>;
  responseHeaders?: Record<string, string>;
  requestBody?: unknown;
  responseBody?: unknown;
  startTime: number;
  endTime?: number;
  duration?: number;
  error?: string;
}

interface CrashReport {
  id: string;
  error: Error;
  componentStack?: string;
  timestamp: number;
}

interface DeviceInfo {
  brand?: string;
  modelName?: string;
  osName?: string;
  osVersion?: string;
  deviceType?: string;
  totalMemory?: number;
}

interface DevOverlayConfig {
  enabled?: boolean;
  shakeToOpen?: boolean;
  showFab?: boolean;
  fabPosition?: { x: number; y: number };
  maxLogs?: number;
  maxNetworkRequests?: number;
}

Examples

Programmatic Control

import { useDevOverlay } from 'tofu-log';

function DebugButton() {
  const { toggle, logs } = useDevOverlay();
  
  return (
    <TouchableOpacity onPress={toggle}>
      <Text>Debug ({logs.length} logs)</Text>
    </TouchableOpacity>
  );
}

Custom Error Handling

import { DevOverlay, useDevOverlay } from 'tofu-log';

function App() {
  return (
    <DevOverlay>
      <ErrorReporter />
      <MainApp />
    </DevOverlay>
  );
}

function ErrorReporter() {
  const { crashReports } = useDevOverlay();
  
  useEffect(() => {
    if (crashReports.length > 0) {
      // Send to your error tracking service
      sendToSentry(crashReports[0]);
    }
  }, [crashReports]);
  
  return null;
}

Requirements

  • React Native 0.70+
  • Expo SDK 48+
  • React 18+

License

MIT © Sergio Morales

Contributing

Contributions are welcome! Please open an issue or submit a pull request.

Changelog

0.1.0

  • Vibe Logger - Terminal-style console output
  • Smart filtering - Clean Metro terminal (only warn/error by default)
  • Push to Terminal - Manually send any log to Metro with one tap
  • Terminal-style Logs tab - ASCII rendering, monospace fonts
  • AI-Ready - Copy for AI, Share reports, Copy as cURL
  • Saturn FAB - Beautiful draggable floating action button with teal theme
  • Network Inspector - Monitor fetch/XHR with detailed headers/bodies
  • Crash Reporter - Error boundary with stack traces and component trees
  • Device Info - View device, OS, app, and runtime information
  • Shake to Open - Shake gesture to toggle debug panel
  • Dark Mode - Designed for long debugging sessions
  • Zero Config - Works out of the box, auto-disabled in production