# metascrape

Official Python client for the **MetaScrape API** -- extract metadata from any URL in one call.

Get Open Graph tags, Twitter Cards, favicons, canonical URLs, and more with a single request. Zero dependencies. Works with Python 3.8+.

## Install

```bash
pip install metascrape
```

## Quick Start

```python
from metascrape import MetaScrape

ms = MetaScrape("your-api-key")

meta = ms.extract("https://example.com")
print(meta["title"])       # "Example Domain"
print(meta["og"]["image"]) # "https://example.com/image.png"
print(meta["description"]) # "An example website"
```

## Getting an API Key

1. Sign up at [metascrape.shanecode.org](https://metascrape.shanecode.org)
2. Your API key is returned on login

Or use the SDK directly:

```python
from metascrape import MetaScrape

# Create an account
MetaScrape.signup("you@example.com", "your-password")

# Login to get your API key
result = MetaScrape.login("you@example.com", "your-password")
print(result["api_key"])  # Use this for all authenticated requests
```

## API Reference

### `MetaScrape(api_key, base_url=None)`

Create a client instance.

| Parameter | Type | Default | Description |
|-----------|------|---------|-------------|
| `api_key` | `str` | *required* | Your MetaScrape API key |
| `base_url` | `str` | `https://api.shanecode.org` | API base URL |

### `ms.extract(url)`

Extract metadata from a URL. Returns the metadata dict directly (envelope is unwrapped).

```python
meta = ms.extract("https://github.com")
```

**Returns:**

| Field | Type | Description |
|-------|------|-------------|
| `title` | `str` | Page title |
| `description` | `str` | Meta description |
| `og` | `dict` | Open Graph tags (title, description, image, type, site_name) |
| `twitter` | `dict` | Twitter Card tags (card, title, description, image, site) |
| `favicon` | `str` | Favicon URL |
| `canonical_url` | `str` | Canonical URL |
| `language` | `str` | Page language |
| `structured_data` | `list` | JSON-LD structured data |
| `response_time_ms` | `int` | Extraction time in milliseconds |

### `ms.usage()`

Get your current month's API usage.

```python
usage = ms.usage()
print(f"{usage['used']} / {usage['limit']} requests used")
```

**Returns:** `{"plan": str, "used": int, "limit": int, "remaining": int}`

### `MetaScrape.signup(email, password, base_url=None)`

Class method. Create a new account. No API key required.

```python
MetaScrape.signup("you@example.com", "secure-password")
```

### `MetaScrape.login(email, password, base_url=None)`

Class method. Login and retrieve your API key. No API key required.

```python
result = MetaScrape.login("you@example.com", "secure-password")
api_key = result["api_key"]
```

## Error Handling

The client raises `MetaScrapeError` for non-2xx responses:

```python
from metascrape import MetaScrape, MetaScrapeError

ms = MetaScrape("your-api-key")

try:
    meta = ms.extract("https://example.com")
except MetaScrapeError as e:
    print(e.status_code)  # 401, 429, etc.
    print(e.message)      # "invalid API key", "rate limit exceeded", etc.
```

## Pricing

| Plan | Requests/month | Price |
|------|---------------|-------|
| Free | 100 | $0 |
| Hobby | 1,000 | $9/mo |
| Growth | 10,000 | $29/mo |
| Business | 100,000 | $79/mo |

Start free at [metascrape.shanecode.org](https://metascrape.shanecode.org).

## Links

- [Full Documentation](https://metascrape.shanecode.org)
- [Sign Up / Get API Key](https://metascrape.shanecode.org)
- [npm Package](https://www.npmjs.com/package/@shanecode/metascrape) (Node.js SDK)
- [ShaneCode](https://shanecode.org)

## License

MIT -- see [LICENSE](./LICENSE)

---

Built by [ShaneCode](https://shanecode.org) -- https://shanecode.org
