query other ip
All checks were successful
Build Docker Image / build (arm64) (push) Successful in 36s
Build Docker Image / build (amd64) (push) Successful in 4m18s
Build Docker Image / amend-manifest (push) Successful in 16s

This commit is contained in:
thuanle
2025-10-13 17:27:14 +07:00
parent f89394be9c
commit 1ef2896fb1
5 changed files with 283 additions and 4 deletions

View File

@@ -48,7 +48,7 @@ jobs:
docker push ${{ env.IMAGE_PATH }}:${{ matrix.arch }}-latest docker push ${{ env.IMAGE_PATH }}:${{ matrix.arch }}-latest
amend-manifest: amend-manifest:
runs-on: ubuntu-latest runs-on: linux
needs: [build] needs: [build]
steps: steps:
- name: Login to Docker Registry - name: Login to Docker Registry

265
README.md Normal file
View File

@@ -0,0 +1,265 @@
# IP Info Service
A high-performance IP geolocation service built with Go that provides detailed information about IP addresses including country, ASN (Autonomous System Number), and other geolocation data.
## Features
- 🌍 IP geolocation lookup with country information
- 🏢 ASN (Autonomous System Number) information
- 🚀 High-performance HTTP API
- 🔄 Automatic database updates
- 🐳 Docker support
- 📊 Metrics endpoint for monitoring
- 🛡️ Input validation and error handling
## Quick Start
### Using Docker (Recommended)
1. Clone the repository:
```bash
git clone <repository-url>
cd ip-info
```
2. Start the service using Docker Compose:
```bash
docker-compose up -d
```
The service will be available at `http://localhost:28080`
### Manual Installation
1. Install Go 1.22 or later
2. Clone and build:
```bash
git clone <repository-url>
cd ip-info
go mod download
go build -o ip-info
./ip-info
```
## API Endpoints
### 1. Get Your IP Information
**Plain Text Response:**
```bash
curl http://localhost:28080/
# Returns: 192.168.1.100
```
**JSON Response:**
```bash
curl http://localhost:28080/json
```
Response:
```json
{
"ip": "192.168.1.100",
"country": "US",
"country_name": "United States",
"asn": "AS15169",
"asn_org": "Google LLC"
}
```
### 2. Look Up Specific IP Address
**Query any IP address:**
```bash
curl http://localhost:28080/8.8.8.8
```
Response:
```json
{
"ip": "8.8.8.8",
"country": "US",
"country_name": "United States",
"asn": "AS15169",
"asn_org": "Google LLC"
}
```
### 3. Metrics Endpoint
Monitor service health and performance:
```bash
curl http://localhost:28080/metrics
```
## Configuration
### Environment Variables
| Variable | Default | Description |
|----------|---------|-------------|
| `API_PORT` | `8080` | Port for the HTTP server |
| `GIN_TRUSTED_PROXY_IP` | - | Trusted proxy IP for client IP detection |
| `GIN_MODE` | `debug` | Gin framework mode (`debug`, `release`) |
### Using .env File
Create a `.env` file in the project root:
```env
API_PORT=8080
GIN_TRUSTED_PROXY_IP=127.0.0.1
GIN_MODE=release
```
## Docker Configuration
### Docker Compose
The included `docker-compose.yml` provides:
- Service on port 28080 (maps to container port 8080)
- Persistent cache volume
- Auto-restart policy
- Vietnam timezone configuration
### Custom Docker Build
```bash
# Build image
docker build -t ip-info .
# Run container
docker run -p 8080:8080 -v $(pwd)/.cache:/app/.cache ip-info
```
## Data Sources
The service automatically downloads and updates IP geolocation databases from:
- **Country Data**: GeoLite2 Country database via jsDelivr CDN
- **ASN Data**: GeoLite2 ASN database via jsDelivr CDN
Database updates happen automatically in the background to ensure data freshness.
## Usage Examples
### Basic IP Lookup
```bash
# Get information about Google's DNS
curl http://localhost:28080/8.8.8.8
# Get information about Cloudflare's DNS
curl http://localhost:28080/1.1.1.1
# Get your own IP info
curl http://localhost:28080/json
```
### Integration Examples
**JavaScript/Node.js:**
```javascript
const response = await fetch('http://localhost:28080/8.8.8.8');
const ipInfo = await response.json();
console.log(ipInfo);
```
**Python:**
```python
import requests
response = requests.get('http://localhost:28080/8.8.8.8')
ip_info = response.json()
print(ip_info)
```
**cURL with jq:**
```bash
curl -s http://localhost:28080/8.8.8.8 | jq .
```
## Response Format
All JSON responses include:
- `ip`: The queried IP address
- `country`: ISO 3166-1 alpha-2 country code
- `country_name`: Full country name
- `asn`: Autonomous System Number (when available)
- `asn_org`: ASN organization name (when available)
## Error Handling
### Invalid IP Address
```bash
curl http://localhost:28080/invalid-ip
```
Response:
```json
{
"error": "invalid ip"
}
```
### Service Unavailable
If the database is not loaded yet:
```
HTTP 500: Try again later
```
## Performance
- **Startup Time**: Database loads automatically on startup
- **Response Time**: Sub-millisecond IP lookups after database load
- **Memory Usage**: Optimized MMDB format for efficient memory usage
- **Concurrency**: Built with Go's excellent concurrency support
## Monitoring
### Health Check
```bash
curl http://localhost:28080/metrics
```
### Logs
The service provides structured JSON logging with different log levels. In Docker:
```bash
docker-compose logs -f ip-info
```
## Development
### Local Development
```bash
# Install dependencies
go mod download
# Run in development mode
go run main.go
# Build for production
go build -o ip-info
```
### Project Structure
```
├── main.go # Application entry point
├── configs/ # Configuration files
├── internal/
│ ├── data/ # Database handling
│ └── services/
│ ├── api/ # HTTP API handlers
│ └── db_updater/ # Database update service
├── pkg/ # Shared packages
├── data/ # Database files (auto-generated)
└── docker-compose.yml # Docker configuration
```
## License
[Add your license information here]
## Contributing
[Add contribution guidelines here]
## Support
For issues and questions, please [open an issue](link-to-issues) or contact the maintainers.

View File

@@ -5,6 +5,6 @@ import (
"net/http" "net/http"
) )
func HandleIp(c *gin.Context) { func HandleMyIp(c *gin.Context) {
c.String(http.StatusOK, c.ClientIP()) c.String(http.StatusOK, c.ClientIP())
} }

View File

@@ -3,12 +3,26 @@ package api
import ( import (
"github.com/gin-gonic/gin" "github.com/gin-gonic/gin"
"github.com/rs/zerolog/log" "github.com/rs/zerolog/log"
"net"
"net/http" "net/http"
"thuanle.me/ip-info/internal/data" "thuanle.me/ip-info/internal/data"
) )
func HandleJson(c *gin.Context) { func HandleJson(c *gin.Context) {
ip := c.ClientIP() ip := c.ClientIP()
HandleIpInfo(c, ip)
}
func HandleOtherIp(c *gin.Context) {
ip := c.Param("ip")
if net.ParseIP(ip) == nil {
c.JSON(http.StatusBadRequest, gin.H{"error": "invalid ip"})
return
}
HandleIpInfo(c, ip)
}
func HandleIpInfo(c *gin.Context, ip string) {
if !data.Ins().IsLoaded() { if !data.Ins().IsLoaded() {
log.Error().Msg("DB is not loaded") log.Error().Msg("DB is not loaded")
c.String(http.StatusInternalServerError, "Try again later") c.String(http.StatusInternalServerError, "Try again later")
@@ -26,5 +40,4 @@ func HandleJson(c *gin.Context) {
ipData["ip"] = ip ipData["ip"] = ip
c.JSON(http.StatusOK, ipData) c.JSON(http.StatusOK, ipData)
} }

View File

@@ -22,9 +22,10 @@ func StartApiService() {
_ = engine.SetTrustedProxies([]string{trustedProxyIP}) _ = engine.SetTrustedProxies([]string{trustedProxyIP})
} }
engine.GET("/", HandleIp) engine.GET("/", HandleMyIp)
engine.GET("/json", HandleJson) engine.GET("/json", HandleJson)
engine.GET("/metrics", HandleMetrics) engine.GET("/metrics", HandleMetrics)
engine.GET("/:ip", HandleOtherIp)
port := os.Getenv(key.EnvApiPort) port := os.Getenv(key.EnvApiPort)
if len(port) == 0 { if len(port) == 0 {