AgentSkillsCN

gcs-husdyr-data

当从GCS查询畜牧与动物数据时自动激活。 适用于CHR登记、猪只迁徙、动物福利、抗生素使用, 动物密度、死亡率、畜群追踪、生猪调运等场景。 关键词:家畜、畜牧、动物、牲畜、CHR、猪、生猪、奶牛、牛、抗生素、动物福利、调运、迁徙

SKILL.md
--- frontmatter
name: gcs-husdyr-data
description: |
  Activates when querying livestock and animal data from GCS.
  Use this skill for: CHR registry, pig movements, animal welfare, antibiotics,
  animal density, mortality rates, herd tracking, svineflytning.
  Keywords: husdyr, livestock, animal, dyr, CHR, svin, pig, ko, cattle, antibiotika, dyrevelfærd, flytning, movement

GCS Husdyr (Livestock) Data Catalog

Livestock data including animal movements, welfare inspections, and herd tracking.

Frontend Metrics Supported

Metric KeyDanish NameDescription
antibiotic_usageAntibiotikaforbrugAntibiotic consumption per animal
animal_densityHusdyrtæthedLivestock units per hectare
animal_welfare_violationsDyrevelfærdsovertrædelserWelfare inspection violations
livestock_unitsDyreenhederTotal livestock units (DE)
pig_movementsSvinetransporterPig transport movements
mortality_rateDødelighedAnimal mortality rate

Key Identifier: CHR Number

CHR (Central Husbandry Register) is the primary identifier for livestock operations.

  • Format: 6 digits (e.g., 123456)
  • Validation: ^\d{6}$
  • Note: One CVR can have multiple CHR numbers (multiple herds/locations)

Available Datasets

Silver Layer

Svineflytning Movements (1.27M rows)

Path: gs://$GCS_BUCKET/silver/svineflytning/*/movements.parquet

ColumnTypeDescriptionExample
movement_idstringUnique movement IDMVT-2024-123456
movement_datedateDate of transport2024-05-15
sender_chr_numberint64Sender herd CHR123456
sender_herd_numberstringSender herd sub-ID1
sender_addressstringSender addressGårdvej 1, 1234 By
sender_municipality_codestringSender municipality0101
receiver_chr_numberint64Receiver herd CHR654321
receiver_herd_numberstringReceiver herd sub-ID2
receiver_addressstringReceiver addressMarkstien 5, 5678 By
receiver_municipality_codestringReceiver municipality0201
total_animalsintTotal animals moved250
sow_countintNumber of sows0
slaughter_pig_countintSlaughter pigs250
piglet_countintNumber of piglets0
boar_countintNumber of boars0
vehicle_registrationstringTransport vehicleAB12345
transport_duration_hoursfloatTransport duration2.5
distance_kmfloatTransport distance45.2

Schema (introspected):

code
movement_id: string
movement_date: date32
sender_chr_number: int64
sender_herd_number: string
sender_address: string
sender_municipality_code: string
receiver_chr_number: int64
receiver_herd_number: string
receiver_address: string
receiver_municipality_code: string
total_animals: int64
sow_count: int64
slaughter_pig_count: int64
piglet_count: int64
boar_count: int64
vehicle_registration: string
[51 columns total]

Animal Welfare Inspections

Path: gs://$GCS_BUCKET/silver/animal welfare/*/data.parquet

ColumnTypeDescription
chr_numberint64Herd CHR number
inspection_datedateDate of inspection
inspection_typestringType of inspection
violations_foundintNumber of violations
violation_categorieslistCategories of violations
compliance_statusstringOverall compliance
follow_up_requiredboolFollow-up needed

Animal Mortality

Path: gs://$GCS_BUCKET/silver/animal mortality/*/data.parquet

ColumnTypeDescription
chr_numberint64Herd CHR number
report_datedateMortality report date
animal_typestringType of animal
mortality_countintNumber of deaths
mortality_rate_pctfloatMortality percentage
cause_categorystringCause of death category

Bronze Layer

CHR Movement Summaries (124K rows)

Path: gs://$GCS_BUCKET/bronze/chr/*/chr_dyr_movement_summaries.parquet

ColumnTypeDescriptionExample
reporting_herd_numberint64CHR number123456
animal_typestringType of animalSvin
period_startdatePeriod start2024-01-01
period_enddatePeriod end2024-03-31
animals_inintAnimals received500
animals_outintAnimals sent450
birthsintAnimals born200
deathsintAnimals died30
animal_countintEnd-of-period count720

Schema (introspected):

code
reporting_herd_number: int64
animal_type: string
period_start: date32
period_end: date32
animals_in: int64
animals_out: int64
births: int64
deaths: int64
animal_count: int64
[11 columns total]

Antibiotic Usage

Path: gs://$GCS_BUCKET/bronze/vetstat/*/antibiotic_usage.parquet

ColumnTypeDescription
chr_numberint64Herd CHR number
prescription_datedateDate of prescription
antibiotic_typestringType of antibiotic
dosage_amountfloatAmount prescribed
dosage_unitstringUnit of measure
treatment_reasonstringReason for treatment

Common Queries

Track Pig Movements for a CHR

python
import pyarrow.parquet as pq
from google.cloud import storage
import io

client = storage.Client()
bucket = client.bucket('$GCS_BUCKET')

# Read svineflytning movements
blob = bucket.blob('silver/svineflytning/2025-01-10/movements.parquet')
buffer = io.BytesIO()
blob.download_to_file(buffer)
buffer.seek(0)
df = pq.read_table(buffer).to_pandas()

chr_number = 123456

# Find all movements involving this CHR (as sender or receiver)
outgoing = df[df['sender_chr_number'] == chr_number]
incoming = df[df['receiver_chr_number'] == chr_number]

print(f"Outgoing movements: {len(outgoing)}, Animals sent: {outgoing['total_animals'].sum()}")
print(f"Incoming movements: {len(incoming)}, Animals received: {incoming['total_animals'].sum()}")

Calculate Animal Density by Municipality

python
# Get movement data to estimate animal counts
movements = df.groupby('receiver_municipality_code').agg({
    'total_animals': 'sum'
}).reset_index()

# Join with land area data (from landbrugsareal skill)
# to calculate animals per hectare

Network Analysis: Farm-to-Farm Connections

python
# Create network of farm connections
import networkx as nx

G = nx.DiGraph()

for _, row in df.iterrows():
    sender = row['sender_chr_number']
    receiver = row['receiver_chr_number']
    animals = row['total_animals']

    if G.has_edge(sender, receiver):
        G[sender][receiver]['weight'] += animals
    else:
        G.add_edge(sender, receiver, weight=animals)

# Find most connected farms
centrality = nx.degree_centrality(G)
top_farms = sorted(centrality.items(), key=lambda x: x[1], reverse=True)[:10]

Movement Patterns Over Time

python
import pandas as pd

# Convert to datetime and aggregate by month
df['movement_month'] = pd.to_datetime(df['movement_date']).dt.to_period('M')

monthly_movements = df.groupby('movement_month').agg({
    'movement_id': 'count',
    'total_animals': 'sum'
}).reset_index()
monthly_movements.columns = ['month', 'movement_count', 'total_animals']

Find High-Volume Transport Routes

python
# Aggregate by sender-receiver municipality pairs
routes = df.groupby(['sender_municipality_code', 'receiver_municipality_code']).agg({
    'total_animals': 'sum',
    'movement_id': 'count'
}).reset_index()
routes.columns = ['from_muni', 'to_muni', 'total_animals', 'trips']

# Top routes
top_routes = routes.nlargest(10, 'total_animals')

Slaughter Pig vs Breeding Stock Analysis

python
# Calculate proportion of different animal types
df['pct_slaughter'] = df['slaughter_pig_count'] / df['total_animals'] * 100
df['pct_sows'] = df['sow_count'] / df['total_animals'] * 100
df['pct_piglets'] = df['piglet_count'] / df['total_animals'] * 100

# Movements by type
slaughter_movements = df[df['slaughter_pig_count'] > 0]
breeding_movements = df[df['sow_count'] > 0]

Join Keys

This DatasetJoin ColumnTarget DatasetTarget Column
svineflytningsender_chr_numberchr_movementsreporting_herd_number
svineflytningreceiver_chr_numberchr_movementsreporting_herd_number
svineflytningsender_municipality_codedagi_kommunercode
svineflytningreceiver_municipality_codedagi_kommunercode
animal_welfarechr_numberchr_movementsreporting_herd_number
antibiotic_usagechr_numberchr_movementsreporting_herd_number

Linking CHR to CVR

CHR numbers link to CVR through the CHR registry (separate lookup):

python
# CHR to CVR mapping typically comes from:
# - bronze/chr/*/chr_bedrifter.parquet
# - Contains chr_number -> cvr_number mapping

Data Quality Notes

Svineflytning

  • Update frequency: Daily/Weekly from Danish Veterinary Authority
  • Coverage: All registered pig movements in Denmark
  • Lag: ~1 week from actual movement to data availability
  • Completeness: Mandatory reporting, high coverage

CHR Movements

  • Update frequency: Quarterly summaries
  • Coverage: All registered herds
  • Note: Summary data, not individual movements

Animal Welfare

  • Update frequency: After inspection completion
  • Coverage: Risk-based inspection regime
  • Caveat: Not all farms inspected every year

Disease Tracing

The svineflytning data is critical for disease outbreak tracing:

python
def trace_contacts(chr_number, df, days_back=21):
    """Find all farms that had contact with a CHR within time window."""
    # Get movement dates for this CHR
    outgoing = df[df['sender_chr_number'] == chr_number]
    incoming = df[df['receiver_chr_number'] == chr_number]

    if len(outgoing) == 0 and len(incoming) == 0:
        return []

    # Get date range
    all_dates = pd.concat([outgoing['movement_date'], incoming['movement_date']])
    max_date = all_dates.max()
    min_date = max_date - pd.Timedelta(days=days_back)

    # Filter to time window
    recent_out = outgoing[outgoing['movement_date'] >= min_date]
    recent_in = incoming[incoming['movement_date'] >= min_date]

    # Get contact CHRs
    contacts = set(recent_out['receiver_chr_number'].tolist())
    contacts.update(recent_in['sender_chr_number'].tolist())
    contacts.discard(chr_number)

    return list(contacts)

Related Skills

  • landbrugsareal/ - Land area for animal density calculations
  • miljo/ - Environmental impact of livestock operations
  • okonomi/ - Subsidies related to animal production
  • medarbejdere/ - Agricultural worker data for livestock operations

GCS Paths Reference

bash
# List svineflytning snapshots
gsutil ls gs://$GCS_BUCKET/silver/svineflytning/

# List CHR data
gsutil ls gs://$GCS_BUCKET/bronze/chr/

# List animal welfare data
gsutil ls gs://$GCS_BUCKET/silver/animal\ welfare/

# List animal mortality data
gsutil ls gs://$GCS_BUCKET/silver/animal\ mortality/

Note on CHR vs CVR

  • CHR identifies a physical location/herd
  • CVR identifies a legal entity (company)
  • One CVR can own multiple CHR (multiple farms/herds)
  • One CHR belongs to exactly one CVR
  • Join using CHR registry lookup tables