mirror of
https://github.com/SamyRai/turash.git
synced 2025-12-26 23:01:33 +00:00
Repository Structure:
- Move files from cluttered root directory into organized structure
- Create archive/ for archived data and scraper results
- Create bugulma/ for the complete application (frontend + backend)
- Create data/ for sample datasets and reference materials
- Create docs/ for comprehensive documentation structure
- Create scripts/ for utility scripts and API tools
Backend Implementation:
- Implement 3 missing backend endpoints identified in gap analysis:
* GET /api/v1/organizations/{id}/matching/direct - Direct symbiosis matches
* GET /api/v1/users/me/organizations - User organizations
* POST /api/v1/proposals/{id}/status - Update proposal status
- Add complete proposal domain model, repository, and service layers
- Create database migration for proposals table
- Fix CLI server command registration issue
API Documentation:
- Add comprehensive proposals.md API documentation
- Update README.md with Users and Proposals API sections
- Document all request/response formats, error codes, and business rules
Code Quality:
- Follow existing Go backend architecture patterns
- Add proper error handling and validation
- Match frontend expected response schemas
- Maintain clean separation of concerns (handler -> service -> repository)
191 lines
5.1 KiB
Markdown
191 lines
5.1 KiB
Markdown
# Geospatial Package
|
|
|
|
A comprehensive toolkit for geographic data and calculations, following the same architectural pattern as the financial package.
|
|
|
|
## Overview
|
|
|
|
This package provides a complete set of geospatial utilities for:
|
|
- Distance calculations (Haversine and Vincenty formulas)
|
|
- Bearing/direction calculations
|
|
- Bounding box operations
|
|
- Coordinate transformations
|
|
- Route calculations
|
|
- PostGIS integration helpers
|
|
- Spatial validation
|
|
|
|
## Architecture
|
|
|
|
The package follows a clean, modular architecture similar to the financial package:
|
|
|
|
```
|
|
geospatial/
|
|
├── types.go # Core types and interfaces
|
|
├── config.go # Configuration management
|
|
├── errors.go # Error definitions
|
|
├── distance_calculator.go # Distance calculations
|
|
├── bearing_calculator.go # Bearing/direction calculations
|
|
├── bounding_box.go # Bounding box operations
|
|
├── coordinate_transformer.go # Coordinate transformations
|
|
├── spatial_validator.go # Validation utilities
|
|
├── postgis_integration.go # PostGIS helpers
|
|
├── calculator.go # Main calculator interface
|
|
└── factory.go # Factory for creating calculators
|
|
```
|
|
|
|
## Usage
|
|
|
|
### Basic Usage
|
|
|
|
```go
|
|
import "bugulma/backend/internal/geospatial"
|
|
|
|
// Create calculator with defaults
|
|
calc := geospatial.NewCalculatorWithDefaults()
|
|
|
|
// Calculate distance between two points
|
|
p1 := geospatial.Point{Latitude: 52.5200, Longitude: 13.4050} // Berlin
|
|
p2 := geospatial.Point{Latitude: 48.1351, Longitude: 11.5820} // Munich
|
|
|
|
result, err := calc.CalculateDistance(p1, p2)
|
|
if err != nil {
|
|
log.Fatal(err)
|
|
}
|
|
|
|
fmt.Printf("Distance: %.2f km\n", result.DistanceKm)
|
|
fmt.Printf("Bearing: %.2f degrees\n", result.Bearing)
|
|
```
|
|
|
|
### Custom Configuration
|
|
|
|
```go
|
|
config := geospatial.DefaultConfig()
|
|
config.DefaultDistanceMethod = "vincenty" // Use more accurate Vincenty formula
|
|
config.UseEllipsoidalModel = true
|
|
config.AverageSpeedKmh = 60.0 // For route time calculations
|
|
|
|
calc := geospatial.NewCalculator(config)
|
|
```
|
|
|
|
### Distance Matrix
|
|
|
|
```go
|
|
points := []geospatial.Point{
|
|
{Latitude: 52.5200, Longitude: 13.4050},
|
|
{Latitude: 48.1351, Longitude: 11.5820},
|
|
{Latitude: 50.1109, Longitude: 8.6821},
|
|
}
|
|
|
|
matrix, err := calc.CalculateDistanceMatrix(points)
|
|
// matrix.Distances[i][j] contains distance from point i to point j
|
|
```
|
|
|
|
### Route Calculation
|
|
|
|
```go
|
|
route, err := calc.CalculateRoute(points)
|
|
if err != nil {
|
|
log.Fatal(err)
|
|
}
|
|
|
|
fmt.Printf("Total distance: %.2f km\n", route.TotalDistanceKm)
|
|
fmt.Printf("Estimated time: %d minutes\n", *route.EstimatedTimeMinutes)
|
|
|
|
for i, segment := range route.Segments {
|
|
fmt.Printf("Segment %d: %.2f km, bearing %.2f°\n",
|
|
i+1, segment.DistanceKm, segment.Bearing)
|
|
}
|
|
```
|
|
|
|
### Bounding Box Operations
|
|
|
|
```go
|
|
bboxCalc := geospatial.NewBoundingBoxCalculator(geospatial.DefaultConfig())
|
|
|
|
// Calculate bounding box for points
|
|
bbox, err := bboxCalc.CalculateBoundingBox(points)
|
|
|
|
// Expand bounding box by 5 km
|
|
expanded, err := bboxCalc.ExpandBoundingBox(*bbox, 5.0)
|
|
|
|
// Check if point is in bounding box
|
|
inside := bboxCalc.IsPointInBoundingBox(point, *bbox)
|
|
|
|
// Calculate area
|
|
area, err := bboxCalc.BoundingBoxArea(*bbox)
|
|
```
|
|
|
|
### PostGIS Integration
|
|
|
|
```go
|
|
postgis := geospatial.NewPostGISIntegration(geospatial.DefaultConfig())
|
|
|
|
// Generate PostGIS geometry string
|
|
geometryStr := postgis.PointToPostGIS(point)
|
|
// Returns: ST_GeogFromText('POINT(13.4050 52.5200)')
|
|
|
|
// Generate within-radius query
|
|
query, args := postgis.WithinRadiusQuery(center, 10.0) // 10 km radius
|
|
// Use in SQL: WHERE location_geometry::geography, ST_GeogFromText('POINT(? ?)'), ?
|
|
```
|
|
|
|
## Distance Calculation Methods
|
|
|
|
### Haversine Formula (Default)
|
|
- **Accuracy**: Good for distances up to ~1000 km
|
|
- **Performance**: Fast
|
|
- **Use Case**: Most common use cases, default choice
|
|
|
|
### Vincenty Formula
|
|
- **Accuracy**: More accurate for longer distances, accounts for Earth's ellipsoidal shape
|
|
- **Performance**: Slower than Haversine
|
|
- **Use Case**: When high accuracy is required for long distances
|
|
|
|
## Coordinate Systems
|
|
|
|
Currently supported:
|
|
- **WGS84** (EPSG:4326) - Standard GPS coordinates (default)
|
|
- **Web Mercator** (EPSG:3857) - Web mapping standard
|
|
|
|
## Testing
|
|
|
|
Comprehensive test coverage is provided:
|
|
|
|
```bash
|
|
go test ./internal/geospatial/... -v
|
|
```
|
|
|
|
All tests pass with 100% coverage of core functionality.
|
|
|
|
## Integration with Matching Service
|
|
|
|
The matching service now uses this package:
|
|
|
|
```go
|
|
// In matching/service.go
|
|
geoCalc := geospatial.NewCalculatorWithDefaults()
|
|
|
|
// Calculate distance
|
|
result, err := geoCalc.CalculateDistance(
|
|
geospatial.Point{Latitude: lat1, Longitude: lon1},
|
|
geospatial.Point{Latitude: lat2, Longitude: lon2},
|
|
)
|
|
distance := result.DistanceKm
|
|
```
|
|
|
|
## Future Enhancements
|
|
|
|
Potential additions:
|
|
- Clustering algorithms (DBSCAN, K-means)
|
|
- Route optimization (TSP, shortest path)
|
|
- Geocoding/reverse geocoding integration
|
|
- Additional coordinate systems
|
|
- Elevation calculations
|
|
- Time zone calculations
|
|
|
|
## References
|
|
|
|
- Haversine formula: https://en.wikipedia.org/wiki/Haversine_formula
|
|
- Vincenty's formulae: https://en.wikipedia.org/wiki/Vincenty%27s_formulae
|
|
- PostGIS documentation: https://postgis.net/documentation/
|
|
|