โ† Back to Index
EN ROUTE TO SITE

Gas Safety Check & Meter Reading

#GSC-2024-1862 ยท British Gas
Today, Dec 4
2:00 PM - 4:00 PM
3.2 miles away
Travel Status
Started 10:45 AM
Time Traveling
15 minutes
ETA
1:48 PM
Distance Remaining
2.1 miles
Traffic
Light
Estimated arrival in
12:35
GPS tracking active
Distance
3.2 miles ยท 12 min
Navigate
42 Manchester Road
Birmingham, West Midlands
B15 2JK
United Kingdom
Job Details
โš ๏ธ Urgent Attention Required URGENT
This job requires immediate action
Job Type Gas Safety Check
Service Category Property
Client British Gas
Location 42 Manchester Road, B15 2JK
Priority Urgent
Completion By Today, 6:00 PM
Our Reference GSC-2024-1862
Customer Info
Mr. David Johnson
Johnson Properties Ltd
07700 123456
Email david.johnson@email.com
Preferred Contact Mobile (Morning)
Helpdesk 0800 123 4567
Customer Ref CUST-12345
Alt Contacts Wife: 07700 654321
Tenant Sarah Johnson - 07700 111222
Site Access !
โš ๏ธ Site Hazards HIGH RISK
Health & Safety Risks: Steep stairs, low ceiling in basement
PPE Required: Safety boots, hard hat in basement area
Parking Street parking available
Key Holder Neighbor - Mrs Smith - 07700 333444
Key Safe Location: Side of property
Code: 1234
Alarm System Yes - Code: 5678
Access Instructions Ring doorbell twice, side gate may be locked
Pets on Site โš ๏ธ Yes - Friendly dog, will be secured in back garden
Occupancy Occupied
Tenant Available Available all day
Work Instructions
๐Ÿ“ Previous Visit Notes
Gate code changed to 1234. Boiler in basement, watch head on stairs. Customer prefers morning appointments.
Visit Reason Annual gas safety inspection required by law
Requirements Check all gas appliances, test carbon monoxide detectors, issue certificate
Est. Duration 45 minutes
PPE Required Standard PPE, safety boots required
Special Equipment โš ๏ธ Gas analyser, CO detector
Notes Customer will be home. Previous issues with boiler pilot light.
Rate Type Urgent
Job Value ยฃ85.00
Property Tasks
Property Type Semi-Detached
Property Size 1,200 sq ft
Condition Good - Well Maintained
Multi-Story Yes - 2 floors
Rooms 4 Bedrooms, 2 Bathrooms
Previous Work Boiler service 6 months ago
Utilities
Water Supply Yes
Electricity Yes
Gas Yes
Electric Meter External meter box - left side of property
Gas Meter External meter box - front of property
Water Meter Under kitchen sink
Internal Stop Tap Kitchen cupboard under sink
External Stop Tap Front garden near boundary
Gas Safety Requirements
Certificate Required Yes
Last Check Date 15/01/2024
Appliances to Check Boiler, Hob, 2x Gas Fires
Images (4)
!
Property Front
10/12/24, 2:30 PM
Floor Plan
08/12/24, 10:15 AM
!
Boiler Location
11/12/24, 3:45 PM
Gas Meter
11/12/24, 3:50 PM
Schedule
Assigned At 12/12/24, 1:15 PM
Accepted At 12/12/24, 1:45 PM
Journey Started 12/12/24, 3:36 PM
Scheduled Date 12/12/2024
Scheduled Time 4:00 PM - 6:00 PM
ETA 3:48 PM

๐Ÿ“– Real-time ETA System Implementation

1. Location Updates & ETA Calculation

// Mobile app sends location every 30 seconds (foreground only)
// POST /api/AgentOwnJobs/update-location
{
  "latitude": 51.5074,
  "longitude": -0.1278,
  "deviceId": "iPhone-123",
  "platform": "iOS"
}

// API Response includes real-time ETA from OSRM
{
  "message": "Location updated successfully",
  "timestamp": "2024-12-12T15:36:00Z",
  "currentJob": {
    "subJobId": 12345,
    "jobReference": "TASK-12345",
    "customerName": "John Smith",
    "address": "42 Example Road",
    "postcode": "SW1A 1AA",
    "scheduledTime": "2024-12-12T16:00:00Z",
    
    // Real-time ETA from OSRM server (xoeraapis.com:5001)
    "eta": "3:48 PM",
    "etaDateTime": "2024-12-12T15:48:00Z",
    "minutesRemaining": 12.0,
    "distanceRemaining": "2.1 miles",
    "durationDisplay": "12 mins",
    
    // Status indicators
    "isLate": false,
    "journeyStartTime": "2024-12-12T15:30:00Z",
    "minutesTraveling": 6.0
  }
}
            

2. Mobile App ETA Display Logic

// Swift - Display ETA from API response
func handleLocationUpdateResponse(_ response: LocationUpdateResponse) {
    guard let job = response.currentJob else { return }
    
    // Update ETA display based on remaining time
    switch job.minutesRemaining {
    case ...0:
        etaLabel.text = "Arriving now"
        etaLabel.textColor = .systemGreen
        progressBar.progress = 1.0
        
    case 0..<1:
        etaLabel.text = "< 1 min"
        etaLabel.textColor = .systemOrange
        
    case 1..<5:
        etaLabel.text = "Arriving in \(Int(job.minutesRemaining)) mins"
        etaLabel.textColor = .systemOrange
        
    default:
        etaLabel.text = "ETA: \(job.eta)"
        etaLabel.textColor = job.isLate ? .systemRed : .label
    }
    
    // Update distance
    distanceLabel.text = job.distanceRemaining
    
    // Update status if late
    if job.isLate {
        statusBanner.backgroundColor = .systemRed
        statusLabel.text = "Running Late"
        // Notify user
        sendLocalNotification("You're running late for \(job.customerName)")
    }
}

// Kotlin - Location updates timer
class LocationUpdateService {
    private val updateInterval = 30_000L // 30 seconds
    
    fun startLocationUpdates() {
        locationTimer = Timer().scheduleAtFixedRate(0, updateInterval) {
            if (hasLocationPermission() && isAppInForeground()) {
                val location = getCurrentLocation()
                sendLocationUpdate(location)
            }
        }
    }
}
            

3. Backend OSRM Integration

// C# - DrivingDistanceService using OSRM
public async Task<DrivingRouteResult> CalculateDrivingRoute(
    decimal fromLat, decimal fromLng, 
    decimal toLat, decimal toLng)
{
    // OSRM API call (coordinates in lng,lat order)
    var url = $"http://xoeraapis.com:5001/route/v1/driving/" +
              $"{fromLng},{fromLat};{toLng},{toLat}" +
              $"?overview=false&geometries=geojson";
    
    var response = await _httpClient.GetAsync(url);
    var result = JsonConvert.DeserializeObject<OsrmResponse>(response);
    
    return new DrivingRouteResult {
        DistanceMeters = route.Distance,
        DurationSeconds = route.Duration,  // Real-time with traffic
        DistanceDisplay = FormatDistance(route.Distance * 0.000621371),
        DurationDisplay = FormatDuration(route.Duration)
    };
}
            

4. Key Implementation Notes

// Important Points:

1. NO BACKGROUND TRACKING
   - Location only sent when app is in foreground
   - Uses "When In Use" permission only
   - Battery friendly approach

2. ETA ALWAYS POSITIVE
   - Backend calculates: DateTime.UtcNow + route.DurationSeconds
   - Never shows negative ETA
   - When arrived: shows "Arriving now" instead of past time

3. REAL-TIME TRAFFIC
   - OSRM considers current traffic conditions
   - ETA updates every 30 seconds with fresh calculation
   - More accurate than static estimates

4. STATUS TRANSITIONS
   - minutesRemaining <= 0: "Arriving now" (green)
   - minutesRemaining < 1: "< 1 min" (orange)
   - minutesRemaining < 5: "Arriving in X mins" (orange)  
   - isLate == true: Show red status, notify user

5. ERROR HANDLING
   - If OSRM fails: Show last known ETA
   - If no location permission: Prompt user
   - If no network: Cache last response
            

5. Data Flow Summary

Mobile App                      Backend                         OSRM Server
----------                      -------                         -----------
[Get Location] โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ–บ [Update Agent Location]
                                       โ”‚
                                       โ”œโ”€โ–บ Save to DB
                                       โ”‚
                                       โ”œโ”€โ–บ Find En Route Job
                                       โ”‚
                                       โ””โ”€โ–บ [Calculate Route] โ”€โ”€โ”€โ”€โ–บ [Route API]
                                                                        โ”‚
[Display ETA] โ—„โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€  [Return ETA Response] โ—„โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”˜

// Response includes:
- eta: "3:48 PM"
- minutesRemaining: 12
- distanceRemaining: "2.1 miles" 
- isLate: false
            

โšก Status Transitions

From Status Action To Status API Call
Scheduled Start Journey En Route POST /api/subjob/{id}/start-journey
En Route I've Arrived On Site POST /api/subjob/{id}/mark-arrived