413 lines
12 KiB
Go
413 lines
12 KiB
Go
// Code generated by sqlc. DO NOT EDIT.
|
||
// versions:
|
||
// sqlc v1.30.0
|
||
// source: geospatial.sql
|
||
|
||
package database
|
||
|
||
import (
|
||
"context"
|
||
|
||
"github.com/jackc/pgx/v5/pgtype"
|
||
)
|
||
|
||
const CountRequestsNearby = `-- name: CountRequestsNearby :one
|
||
|
||
SELECT COUNT(*) FROM requests r
|
||
WHERE r.deleted_at IS NULL
|
||
AND r.status = $3
|
||
AND ST_DWithin(
|
||
r.location,
|
||
ST_SetSRID(ST_MakePoint($1, $2), 4326)::geography,
|
||
$4
|
||
)
|
||
`
|
||
|
||
type CountRequestsNearbyParams struct {
|
||
StMakepoint interface{} `json:"st_makepoint"`
|
||
StMakepoint_2 interface{} `json:"st_makepoint_2"`
|
||
Status NullRequestStatus `json:"status"`
|
||
StDwithin interface{} `json:"st_dwithin"`
|
||
}
|
||
|
||
// ============================================================================
|
||
// Подсчет заявок поблизости
|
||
// ============================================================================
|
||
func (q *Queries) CountRequestsNearby(ctx context.Context, arg CountRequestsNearbyParams) (int64, error) {
|
||
row := q.db.QueryRow(ctx, CountRequestsNearby,
|
||
arg.StMakepoint,
|
||
arg.StMakepoint_2,
|
||
arg.Status,
|
||
arg.StDwithin,
|
||
)
|
||
var count int64
|
||
err := row.Scan(&count)
|
||
return count, err
|
||
}
|
||
|
||
const FindNearestRequestsForVolunteer = `-- name: FindNearestRequestsForVolunteer :many
|
||
|
||
SELECT
|
||
r.id,
|
||
r.title,
|
||
r.description,
|
||
r.urgency,
|
||
r.status,
|
||
r.created_at,
|
||
ST_Y(r.location::geometry) as latitude,
|
||
ST_X(r.location::geometry) as longitude,
|
||
ST_Distance(
|
||
r.location,
|
||
(SELECT u.location FROM users u WHERE u.id = $1)
|
||
) as distance_meters,
|
||
rt.name as request_type_name,
|
||
rt.icon as request_type_icon
|
||
FROM requests r
|
||
JOIN request_types rt ON rt.id = r.request_type_id
|
||
WHERE r.deleted_at IS NULL
|
||
AND r.status = 'approved'
|
||
AND r.assigned_volunteer_id IS NULL
|
||
AND ST_DWithin(
|
||
r.location,
|
||
(SELECT u.location FROM users u WHERE u.id = $1),
|
||
$2
|
||
)
|
||
ORDER BY
|
||
CASE r.urgency
|
||
WHEN 'urgent' THEN 1
|
||
WHEN 'high' THEN 2
|
||
WHEN 'medium' THEN 3
|
||
ELSE 4
|
||
END,
|
||
distance_meters
|
||
LIMIT $3
|
||
`
|
||
|
||
type FindNearestRequestsForVolunteerParams struct {
|
||
ID int64 `json:"id"`
|
||
StDwithin interface{} `json:"st_dwithin"`
|
||
Limit int32 `json:"limit"`
|
||
}
|
||
|
||
type FindNearestRequestsForVolunteerRow struct {
|
||
ID int64 `json:"id"`
|
||
Title string `json:"title"`
|
||
Description string `json:"description"`
|
||
Urgency pgtype.Text `json:"urgency"`
|
||
Status NullRequestStatus `json:"status"`
|
||
CreatedAt pgtype.Timestamptz `json:"created_at"`
|
||
Latitude interface{} `json:"latitude"`
|
||
Longitude interface{} `json:"longitude"`
|
||
DistanceMeters interface{} `json:"distance_meters"`
|
||
RequestTypeName string `json:"request_type_name"`
|
||
RequestTypeIcon pgtype.Text `json:"request_type_icon"`
|
||
}
|
||
|
||
// ============================================================================
|
||
// Поиск ближайших заявок для волонтера
|
||
// ============================================================================
|
||
func (q *Queries) FindNearestRequestsForVolunteer(ctx context.Context, arg FindNearestRequestsForVolunteerParams) ([]FindNearestRequestsForVolunteerRow, error) {
|
||
rows, err := q.db.Query(ctx, FindNearestRequestsForVolunteer, arg.ID, arg.StDwithin, arg.Limit)
|
||
if err != nil {
|
||
return nil, err
|
||
}
|
||
defer rows.Close()
|
||
items := []FindNearestRequestsForVolunteerRow{}
|
||
for rows.Next() {
|
||
var i FindNearestRequestsForVolunteerRow
|
||
if err := rows.Scan(
|
||
&i.ID,
|
||
&i.Title,
|
||
&i.Description,
|
||
&i.Urgency,
|
||
&i.Status,
|
||
&i.CreatedAt,
|
||
&i.Latitude,
|
||
&i.Longitude,
|
||
&i.DistanceMeters,
|
||
&i.RequestTypeName,
|
||
&i.RequestTypeIcon,
|
||
); err != nil {
|
||
return nil, err
|
||
}
|
||
items = append(items, i)
|
||
}
|
||
if err := rows.Err(); err != nil {
|
||
return nil, err
|
||
}
|
||
return items, nil
|
||
}
|
||
|
||
const FindRequestsInBounds = `-- name: FindRequestsInBounds :many
|
||
|
||
SELECT
|
||
r.id,
|
||
r.title,
|
||
r.urgency,
|
||
r.status,
|
||
r.created_at,
|
||
ST_Y(r.location::geometry) as latitude,
|
||
ST_X(r.location::geometry) as longitude,
|
||
rt.icon as request_type_icon,
|
||
rt.name as request_type_name
|
||
FROM requests r
|
||
JOIN request_types rt ON rt.id = r.request_type_id
|
||
WHERE r.deleted_at IS NULL
|
||
AND r.status::text = ANY($1::text[])
|
||
AND ST_Within(
|
||
r.location::geometry,
|
||
ST_MakeEnvelope($2, $3, $4, $5, 4326)
|
||
)
|
||
ORDER BY r.created_at DESC
|
||
LIMIT 200
|
||
`
|
||
|
||
type FindRequestsInBoundsParams struct {
|
||
Column1 []string `json:"column_1"`
|
||
StMakeenvelope interface{} `json:"st_makeenvelope"`
|
||
StMakeenvelope_2 interface{} `json:"st_makeenvelope_2"`
|
||
StMakeenvelope_3 interface{} `json:"st_makeenvelope_3"`
|
||
StMakeenvelope_4 interface{} `json:"st_makeenvelope_4"`
|
||
}
|
||
|
||
type FindRequestsInBoundsRow struct {
|
||
ID int64 `json:"id"`
|
||
Title string `json:"title"`
|
||
Urgency pgtype.Text `json:"urgency"`
|
||
Status NullRequestStatus `json:"status"`
|
||
CreatedAt pgtype.Timestamptz `json:"created_at"`
|
||
Latitude interface{} `json:"latitude"`
|
||
Longitude interface{} `json:"longitude"`
|
||
RequestTypeIcon pgtype.Text `json:"request_type_icon"`
|
||
RequestTypeName string `json:"request_type_name"`
|
||
}
|
||
|
||
// ============================================================================
|
||
// Поиск заявок в прямоугольной области (для карты)
|
||
// ============================================================================
|
||
func (q *Queries) FindRequestsInBounds(ctx context.Context, arg FindRequestsInBoundsParams) ([]FindRequestsInBoundsRow, error) {
|
||
rows, err := q.db.Query(ctx, FindRequestsInBounds,
|
||
arg.Column1,
|
||
arg.StMakeenvelope,
|
||
arg.StMakeenvelope_2,
|
||
arg.StMakeenvelope_3,
|
||
arg.StMakeenvelope_4,
|
||
)
|
||
if err != nil {
|
||
return nil, err
|
||
}
|
||
defer rows.Close()
|
||
items := []FindRequestsInBoundsRow{}
|
||
for rows.Next() {
|
||
var i FindRequestsInBoundsRow
|
||
if err := rows.Scan(
|
||
&i.ID,
|
||
&i.Title,
|
||
&i.Urgency,
|
||
&i.Status,
|
||
&i.CreatedAt,
|
||
&i.Latitude,
|
||
&i.Longitude,
|
||
&i.RequestTypeIcon,
|
||
&i.RequestTypeName,
|
||
); err != nil {
|
||
return nil, err
|
||
}
|
||
items = append(items, i)
|
||
}
|
||
if err := rows.Err(); err != nil {
|
||
return nil, err
|
||
}
|
||
return items, nil
|
||
}
|
||
|
||
const FindRequestsNearby = `-- name: FindRequestsNearby :many
|
||
|
||
|
||
SELECT
|
||
r.id,
|
||
r.title,
|
||
r.description,
|
||
r.address,
|
||
r.city,
|
||
r.urgency,
|
||
r.status,
|
||
r.created_at,
|
||
r.desired_completion_date,
|
||
ST_Y(r.location::geometry) as latitude,
|
||
ST_X(r.location::geometry) as longitude,
|
||
ST_Distance(
|
||
r.location,
|
||
ST_SetSRID(ST_MakePoint($1, $2), 4326)::geography
|
||
) as distance_meters,
|
||
rt.name as request_type_name,
|
||
rt.icon as request_type_icon,
|
||
(u.first_name || ' ' || u.last_name) as requester_name
|
||
FROM requests r
|
||
JOIN request_types rt ON rt.id = r.request_type_id
|
||
JOIN users u ON u.id = r.requester_id
|
||
WHERE r.deleted_at IS NULL
|
||
AND r.status::text = ANY($3::text[])
|
||
AND ST_DWithin(
|
||
r.location,
|
||
ST_SetSRID(ST_MakePoint($1, $2), 4326)::geography,
|
||
$4
|
||
)
|
||
ORDER BY distance_meters
|
||
LIMIT $5 OFFSET $6
|
||
`
|
||
|
||
type FindRequestsNearbyParams struct {
|
||
StMakepoint interface{} `json:"st_makepoint"`
|
||
StMakepoint_2 interface{} `json:"st_makepoint_2"`
|
||
Column3 []string `json:"column_3"`
|
||
StDwithin interface{} `json:"st_dwithin"`
|
||
Limit int32 `json:"limit"`
|
||
Offset int32 `json:"offset"`
|
||
}
|
||
|
||
type FindRequestsNearbyRow struct {
|
||
ID int64 `json:"id"`
|
||
Title string `json:"title"`
|
||
Description string `json:"description"`
|
||
Address string `json:"address"`
|
||
City pgtype.Text `json:"city"`
|
||
Urgency pgtype.Text `json:"urgency"`
|
||
Status NullRequestStatus `json:"status"`
|
||
CreatedAt pgtype.Timestamptz `json:"created_at"`
|
||
DesiredCompletionDate pgtype.Timestamptz `json:"desired_completion_date"`
|
||
Latitude interface{} `json:"latitude"`
|
||
Longitude interface{} `json:"longitude"`
|
||
DistanceMeters interface{} `json:"distance_meters"`
|
||
RequestTypeName string `json:"request_type_name"`
|
||
RequestTypeIcon pgtype.Text `json:"request_type_icon"`
|
||
RequesterName interface{} `json:"requester_name"`
|
||
}
|
||
|
||
// Фаза 2B: Геопространственные запросы (ВЫСОКИЙ ПРИОРИТЕТ)
|
||
// PostGIS запросы для поиска заявок по геолокации
|
||
// ============================================================================
|
||
// Поиск заявок рядом с точкой
|
||
// ============================================================================
|
||
func (q *Queries) FindRequestsNearby(ctx context.Context, arg FindRequestsNearbyParams) ([]FindRequestsNearbyRow, error) {
|
||
rows, err := q.db.Query(ctx, FindRequestsNearby,
|
||
arg.StMakepoint,
|
||
arg.StMakepoint_2,
|
||
arg.Column3,
|
||
arg.StDwithin,
|
||
arg.Limit,
|
||
arg.Offset,
|
||
)
|
||
if err != nil {
|
||
return nil, err
|
||
}
|
||
defer rows.Close()
|
||
items := []FindRequestsNearbyRow{}
|
||
for rows.Next() {
|
||
var i FindRequestsNearbyRow
|
||
if err := rows.Scan(
|
||
&i.ID,
|
||
&i.Title,
|
||
&i.Description,
|
||
&i.Address,
|
||
&i.City,
|
||
&i.Urgency,
|
||
&i.Status,
|
||
&i.CreatedAt,
|
||
&i.DesiredCompletionDate,
|
||
&i.Latitude,
|
||
&i.Longitude,
|
||
&i.DistanceMeters,
|
||
&i.RequestTypeName,
|
||
&i.RequestTypeIcon,
|
||
&i.RequesterName,
|
||
); err != nil {
|
||
return nil, err
|
||
}
|
||
items = append(items, i)
|
||
}
|
||
if err := rows.Err(); err != nil {
|
||
return nil, err
|
||
}
|
||
return items, nil
|
||
}
|
||
|
||
const FindVolunteersNearRequest = `-- name: FindVolunteersNearRequest :many
|
||
|
||
SELECT
|
||
u.id,
|
||
(u.first_name || ' ' || u.last_name) as full_name,
|
||
u.avatar_url,
|
||
u.volunteer_rating,
|
||
u.completed_requests_count,
|
||
ST_Y(u.location::geometry) as latitude,
|
||
ST_X(u.location::geometry) as longitude,
|
||
ST_Distance(
|
||
u.location,
|
||
(SELECT req.location FROM requests req WHERE req.id = $1)
|
||
) as distance_meters
|
||
FROM users u
|
||
JOIN user_roles ur ON ur.user_id = u.id
|
||
JOIN roles r ON r.id = ur.role_id
|
||
WHERE r.name = 'volunteer'
|
||
AND u.deleted_at IS NULL
|
||
AND u.is_blocked = FALSE
|
||
AND u.location IS NOT NULL
|
||
AND ST_DWithin(
|
||
u.location,
|
||
(SELECT req.location FROM requests req WHERE req.id = $1),
|
||
$2
|
||
)
|
||
ORDER BY distance_meters
|
||
LIMIT $3
|
||
`
|
||
|
||
type FindVolunteersNearRequestParams struct {
|
||
ID int64 `json:"id"`
|
||
StDwithin interface{} `json:"st_dwithin"`
|
||
Limit int32 `json:"limit"`
|
||
}
|
||
|
||
type FindVolunteersNearRequestRow struct {
|
||
ID int64 `json:"id"`
|
||
FullName interface{} `json:"full_name"`
|
||
AvatarUrl pgtype.Text `json:"avatar_url"`
|
||
VolunteerRating pgtype.Numeric `json:"volunteer_rating"`
|
||
CompletedRequestsCount pgtype.Int4 `json:"completed_requests_count"`
|
||
Latitude interface{} `json:"latitude"`
|
||
Longitude interface{} `json:"longitude"`
|
||
DistanceMeters interface{} `json:"distance_meters"`
|
||
}
|
||
|
||
// ============================================================================
|
||
// Поиск волонтеров рядом с заявкой
|
||
// ============================================================================
|
||
func (q *Queries) FindVolunteersNearRequest(ctx context.Context, arg FindVolunteersNearRequestParams) ([]FindVolunteersNearRequestRow, error) {
|
||
rows, err := q.db.Query(ctx, FindVolunteersNearRequest, arg.ID, arg.StDwithin, arg.Limit)
|
||
if err != nil {
|
||
return nil, err
|
||
}
|
||
defer rows.Close()
|
||
items := []FindVolunteersNearRequestRow{}
|
||
for rows.Next() {
|
||
var i FindVolunteersNearRequestRow
|
||
if err := rows.Scan(
|
||
&i.ID,
|
||
&i.FullName,
|
||
&i.AvatarUrl,
|
||
&i.VolunteerRating,
|
||
&i.CompletedRequestsCount,
|
||
&i.Latitude,
|
||
&i.Longitude,
|
||
&i.DistanceMeters,
|
||
); err != nil {
|
||
return nil, err
|
||
}
|
||
items = append(items, i)
|
||
}
|
||
if err := rows.Err(); err != nil {
|
||
return nil, err
|
||
}
|
||
return items, nil
|
||
}
|