Jofax commited on
Commit
eeebb74
Β·
verified Β·
1 Parent(s): daa2a47

Upload 4 files

Browse files
Files changed (4) hide show
  1. App.y (1).txt +91 -0
  2. README.md +5 -5
  3. app.py +147 -0
  4. gitattributes.txt +35 -0
App.y (1).txt ADDED
@@ -0,0 +1,91 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import gradio as gr
2
+ import pandas as pd
3
+ from datetime import datetime
4
+
5
+ # --- MODERN LIGHTWEIGHT CSS (2026 GLASSMORPHISM STYLE) ---
6
+ theme_css = """
7
+ :root {
8
+ --accent: #00ADEE; /* Maldives Sea Blue */
9
+ --surface: #ffffff;
10
+ --text-main: #1A202C;
11
+ --glass: rgba(255, 255, 255, 0.8);
12
+ }
13
+ .gradio-container { background-color: #F7FAFC !important; font-family: 'Inter', sans-serif !important; }
14
+ .filter-card { background: var(--glass); backdrop-filter: blur(10px); border-radius: 12px; padding: 20px; border: 1px solid #E2E8F0; }
15
+ .hotel-card { border: 1px solid #E2E8F0; border-radius: 12px; transition: 0.3s; }
16
+ .hotel-card:hover { transform: translateY(-3px); box-shadow: 0 10px 20px rgba(0,0,0,0.05); }
17
+ .verified-badge { background: #E3FCEF; color: #006644; padding: 2px 8px; border-radius: 4px; font-size: 0.75em; font-weight: bold; }
18
+ """
19
+
20
+ # --- MOCK DATABASE ---
21
+ initial_data = [
22
+ {"ID": 1, "Name": "Velana Transit Day Inn", "Atoll": "Kaafu", "Location": "Hulhumale", "Price": 800, "Status": "Available", "Verified": True, "Contact": "+960 7771234"},
23
+ {"ID": 2, "Name": "Maafushi Sunset View", "Atoll": "Kaafu", "Location": "Maafushi", "Price": 1200, "Status": "Available", "Verified": True, "Contact": "+960 7775566"},
24
+ ]
25
+ db = pd.DataFrame(initial_data)
26
+
27
+ # --- LOGIC ---
28
+ def register_property(name, location, price, license_img):
29
+ # In a real app, license_img would be processed by an OCR/Admin
30
+ return f"✨ Request received for **{name}**. Our team will verify your license within 24 hours."
31
+
32
+ def filter_results(query):
33
+ if not query: return db
34
+ return db[db['Location'].str.contains(query, case=False) | db['Atoll'].str.contains(query, case=False)]
35
+
36
+ # --- UI LAYOUT ---
37
+ with gr.Blocks(css=theme_css, title="Maldives Direct") as demo:
38
+ gr.HTML("""
39
+ <div style="text-align: center; padding: 20px;">
40
+ <h1 style="color: #00ADEE; font-size: 2.5em; margin-bottom: 0;">MALDIVES DIRECT</h1>
41
+ <p style="color: #718096;">Verified Accommodations β€’ Direct Owner Contact β€’ 0% Commission</p>
42
+ </div>
43
+ """)
44
+
45
+ with gr.Tabs() as main_tabs:
46
+ # CUSTOMER INTERFACE
47
+ with gr.Tab("🏝️ Find a Room"):
48
+ with gr.Row(elem_classes="filter-card"):
49
+ search_input = gr.Textbox(placeholder="Search Island, Atoll or Hotel...", label="Where are you heading?", scale=4)
50
+ filter_btn = gr.Button("πŸ” Search", variant="primary", scale=1)
51
+
52
+ results_table = gr.Dataframe(
53
+ value=db,
54
+ headers=["Name", "Atoll", "Location", "Price (MVR)", "Status", "Contact"],
55
+ datatype=["markdown", "str", "str", "number", "str", "str"],
56
+ interactive=False,
57
+ wrap=True
58
+ )
59
+
60
+ # OWNER INTERFACE (SELF-REGISTRATION)
61
+ with gr.Tab("🏨 For Owners"):
62
+ with gr.Row():
63
+ with gr.Column(scale=1):
64
+ gr.Markdown("### πŸš€ Register Your Property\nJoin the 0% commission movement.")
65
+ reg_name = gr.Textbox(label="Property Name")
66
+ reg_loc = gr.Dropdown(choices=["Male'", "Hulhumale", "Maafushi", "Thulusdhoo", "Dhiffushi"], label="Location")
67
+ reg_price = gr.Number(label="Base Price per Night (MVR)")
68
+ reg_license = gr.Image(label="Upload MOT License / ID Card", type="filepath")
69
+ reg_btn = gr.Button("Submit for Verification", variant="primary")
70
+ reg_output = gr.Markdown()
71
+
72
+ with gr.Column(scale=1):
73
+ gr.HTML("""
74
+ <div style="background: #EBF8FF; padding: 20px; border-radius: 12px; border-left: 5px solid #3182CE;">
75
+ <h4 style="margin-top:0;">Why list with us?</h4>
76
+ <ul style="color: #2C5282; line-height: 1.6;">
77
+ <li><b>Instant Payouts:</b> Guests pay you directly.</li>
78
+ <li><b>Verified Trust:</b> Every listing is vetted by locals.</li>
79
+ <li><b>Low Flat Fee:</b> No commission, just a small monthly sub.</li>
80
+ </ul>
81
+ </div>
82
+ """)
83
+
84
+ # --- ACTIONS ---
85
+ filter_btn.click(fn=filter_results, inputs=search_input, outputs=results_table)
86
+ reg_btn.click(fn=register_property, inputs=[reg_name, reg_loc, reg_price, reg_license], outputs=reg_output)
87
+
88
+ gr.HTML("<p style='text-align:center; color: #A0AEC0; padding: 20px;'>Β© 2026 Maldives Direct - Empowering Local Hospitality</p>")
89
+
90
+ if __name__ == "__main__":
91
+ demo.launch()
README.md CHANGED
@@ -1,10 +1,10 @@
1
  ---
2
- title: Odilink
3
- emoji: 🐒
4
- colorFrom: yellow
5
- colorTo: pink
6
  sdk: gradio
7
- sdk_version: 6.6.0
8
  app_file: app.py
9
  pinned: false
10
  ---
 
1
  ---
2
+ title: Gstay
3
+ emoji: πŸ“Š
4
+ colorFrom: blue
5
+ colorTo: yellow
6
  sdk: gradio
7
+ sdk_version: 6.5.1
8
  app_file: app.py
9
  pinned: false
10
  ---
app.py ADDED
@@ -0,0 +1,147 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import gradio as gr
2
+ import random
3
+ import pandas as pd
4
+ from datetime import datetime
5
+
6
+ # ──────────────────────────────────────────────────────────
7
+ # 1. THE ELITE DATA ENGINE (A-Z List Integration)
8
+ # ──────────────────────────────────────────────────────────
9
+
10
+ # This is a sample of your A-Z list formatted for the search engine
11
+ VESSEL_DATABASE = [
12
+ {"id": "13673", "name": "Balma 11", "type": "Supply Boat", "atoll": "Kaafu", "location": "K. Villingili", "contact": "7791155", "seats": 0, "price": 1500, "icon": "🚒"},
13
+ {"name": "Bankaru Speed", "id": "12929", "type": "Speed Boat", "atoll": "Dhaalu", "location": "Dh. Kudahuvadhoo", "contact": "9494600", "seats": 12, "price": 350, "icon": "🚀"},
14
+ {"name": "Blue Star 9", "id": "16627", "type": "Speed Boat", "atoll": "Raa", "location": "R. Ifuru", "contact": "9827591", "seats": 18, "price": 450, "icon": "🚀"},
15
+ {"name": "Coral Express", "id": "8029", "type": "Speed Boat", "atoll": "Alif Alif", "location": "AA. Ukulhas", "contact": "7783518", "seats": 25, "price": 300, "icon": "🚀"},
16
+ {"name": "Dream Speed 3", "id": "17547", "type": "Speed Boat", "atoll": "Vaavu", "location": "V. Felidhoo", "contact": "9748978", "seats": 20, "price": 400, "icon": "🚀"},
17
+ {"name": "Inaya 2", "id": "17544", "type": "Supply Boat", "atoll": "Thaa", "location": "Th. Thimarafushi", "contact": "7713431", "seats": 0, "price": 2500, "icon": "🚒"},
18
+ ]
19
+
20
+ CARGO_CONTRACTS = [
21
+ {"title": "Resort Logistics", "route": "Male to Baa Atoll", "items": "12 Pallets Food", "budget": 8500, "closes": "4h"},
22
+ {"title": "Construction", "route": "Male to Hulhumale", "items": "200 Bags Cement", "budget": 3000, "closes": "12h"},
23
+ ]
24
+
25
+ # ──────────────────────────────────────────────────────────
26
+ # 2. CORE LOGIC FUNCTIONS
27
+ # ──────────────────────────────────────────────────────────
28
+
29
+ def search_vessels(atoll_filter, type_filter):
30
+ results = VESSEL_DATABASE
31
+ if atoll_filter != "All Atolls":
32
+ results = [v for v in results if v["atoll"] == atoll_filter]
33
+ if type_filter != "All Types":
34
+ results = [v for v in results if v["type"] == type_filter]
35
+
36
+ if not results:
37
+ return "<p style='color:gray;'>No vessels found for this criteria.</p>"
38
+
39
+ html = '<div style="display: grid; grid-template-columns: repeat(auto-fill, minmax(250px, 1fr)); gap: 15px;">'
40
+ for v in results:
41
+ gps_link = f"https://m.followme.mv/public/?id={v.get('id', '')}"
42
+ html += f"""
43
+ <div style="background: #062a4a; border: 1px solid #00b4d8; border-radius: 12px; padding: 15px; color: white;">
44
+ <div style="font-size: 24px;">{v['icon']}</div>
45
+ <div style="font-weight: bold; font-size: 18px;">{v['name']}</div>
46
+ <div style="font-size: 12px; color: #48cae4;">{v['type']} β€’ {v['atoll']}</div>
47
+ <hr style="border: 0.5px solid #1a3a5a; margin: 10px 0;">
48
+ <div style="font-size: 11px;">πŸ“ Last: {v['location']}</div>
49
+ <div style="font-size: 13px; margin-top: 5px;">πŸ“ž {v['contact']}</div>
50
+ <a href="{gps_link}" target="_blank" style="display: block; margin-top: 10px; text-align: center; background: #00b4d8; color: white; text-decoration: none; padding: 5px; border-radius: 5px; font-size: 12px;">πŸ›°οΈ View Live GPS</a>
51
+ </div>
52
+ """
53
+ html += "</div>"
54
+ return html
55
+
56
+ def process_ticket(v_name, p_name, p_seats):
57
+ vessel = next((v for v in VESSEL_DATABASE if v["name"] == v_name), None)
58
+ if not vessel or vessel['seats'] == 0:
59
+ return "⚠️ This vessel does not support passenger ticketing.", ""
60
+
61
+ t_id = f"ALEX-{random.randint(1000, 9999)}"
62
+ total = vessel['price'] * p_seats
63
+ fee = round(total * 0.05, 2)
64
+
65
+ ticket_html = f"""
66
+ <div style="border: 2px dashed #d4a843; padding: 20px; border-radius: 15px; background: #041c35; color: white;">
67
+ <h2 style="color: #d4a843; margin-top: 0;">🎫 OFFICIAL TICKET: {t_id}</h2>
68
+ <p><b>Vessel:</b> {v_name}<br><b>Passenger:</b> {p_name}<br><b>Seats:</b> {p_seats}</p>
69
+ <div style="font-size: 20px; font-weight: bold; color: #48cae4;">Total: MVR {total + fee}</div>
70
+ <p style="font-size: 10px;">(Includes 5% Platform Escrow Fee: MVR {fee})</p>
71
+ <p style="background: #22c55e; color: black; padding: 5px; text-align: center; font-weight: bold;">VALID FOR BOARDING</p>
72
+ </div>
73
+ """
74
+ return ticket_html, f"Admin: Earned MVR {fee} commission."
75
+
76
+ # ──────────────────────────────────────────────────────────
77
+ # 3. PREMIUM UI DESIGN (CSS)
78
+ # ──────────────────────────────────────────────────────────
79
+
80
+ CSS = """
81
+ body, .gradio-container { background-color: #020d1a !important; color: #f8fafc !important; }
82
+ .tabs { border: none !important; }
83
+ .tab-nav { background: #041c35 !important; }
84
+ button.primary { background: linear-gradient(135deg, #00b4d8, #0a4a6b) !important; border: none !important; }
85
+ """
86
+
87
+ # ──────────────────────────────────────────────────────────
88
+ # 4. GRADIO APP LAYOUT
89
+ # ──────────────────────────────────────────────────────────
90
+
91
+ with gr.Blocks(css=CSS, title="ALEX - Maldives Maritime Exchange") as demo:
92
+ gr.HTML("""
93
+ <div style="text-align: center; padding: 20px; background: linear-gradient(135deg, #041c35, #020d1a);">
94
+ <h1 style="font-size: 40px; color: #48cae4; margin-bottom: 0;">ALEX</h1>
95
+ <p style="letter-spacing: 2px; color: #8baac0;">ARCHIPELAGO LOGISTICS EXCHANGE</p>
96
+ </div>
97
+ """)
98
+
99
+ with gr.Tabs():
100
+ # TAB 1: SEARCH
101
+ with gr.Tab("🚒 Vessel Search"):
102
+ with gr.Row():
103
+ atoll_in = gr.Dropdown(["All Atolls", "Kaafu", "Dhaalu", "Raa", "Alif Alif", "Vaavu", "Thaa"], label="Filter by Atoll", value="All Atolls")
104
+ type_in = gr.Dropdown(["All Types", "Speed Boat", "Supply Boat", "Dhoni"], label="Vessel Type", value="All Types")
105
+ search_btn = gr.Button("Find Available Vessels", variant="primary")
106
+ results_out = gr.HTML()
107
+ search_btn.click(search_vessels, [atoll_in, type_in], results_out)
108
+
109
+ # TAB 2: TICKETING
110
+ with gr.Tab("🎫 Elite Ticketing"):
111
+ with gr.Row():
112
+ with gr.Column():
113
+ v_select = gr.Dropdown([v["name"] for v in VESSEL_DATABASE if v["seats"] > 0], label="Select Speedboat")
114
+ p_name = gr.Textbox(label="Passenger Name")
115
+ p_seats = gr.Number(label="Seats", value=1)
116
+ book_btn = gr.Button("Issue Digital Ticket", variant="primary")
117
+ with gr.Column():
118
+ ticket_disp = gr.HTML()
119
+ book_btn.click(process_ticket, [v_select, p_name, p_seats], [ticket_disp, gr.Markdown()])
120
+
121
+ # TAB 3: CARGO BIDDING
122
+ with gr.Tab("πŸ“¦ Cargo Bids"):
123
+ gr.Markdown("### 🚒 Open Cargo Contracts (Bidding Mode)")
124
+ cargo_list = pd.DataFrame(CARGO_CONTRACTS)
125
+ gr.Dataframe(cargo_list, interactive=False)
126
+ with gr.Row():
127
+ bid_amt = gr.Number(label="Enter Your Bid (MVR)")
128
+ v_reg = gr.Textbox(label="Your Vessel Name")
129
+ submit_bid = gr.Button("Submit Formal Bid")
130
+
131
+ # TAB 4: ADMIN DASHBOARD
132
+ with gr.Tab("πŸ“Š Dashboard"):
133
+ with gr.Row():
134
+ gr.Number(label="Active Fleet", value=len(VESSEL_DATABASE), interactive=False)
135
+ gr.Number(label="Total Daily Revenue (MVR)", value=12450, interactive=False)
136
+ gr.Number(label="Platform Commission (5%)", value=622.50, interactive=False)
137
+ gr.Markdown("#### System Audit Log")
138
+ gr.Code("2026-02-19 07:10: TKT-4492 Issued for Blue Star 9\n2026-02-19 06:45: New Cargo Bid from Maafushi Express", language="python")
139
+
140
+ gr.Markdown("---")
141
+ gr.Markdown("πŸ›οΈ **ALEX: Republic of Maldives Elite Maritime Network** | Powered by FollowMe GPS Data")
142
+
143
+ # ──────────────────────────────────────────────────────────
144
+ # 5. EXECUTION
145
+ # ──────────────────────────────────────────────────────────
146
+ if __name__ == "__main__":
147
+ demo.launch()
gitattributes.txt ADDED
@@ -0,0 +1,35 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ *.7z filter=lfs diff=lfs merge=lfs -text
2
+ *.arrow filter=lfs diff=lfs merge=lfs -text
3
+ *.bin filter=lfs diff=lfs merge=lfs -text
4
+ *.bz2 filter=lfs diff=lfs merge=lfs -text
5
+ *.ckpt filter=lfs diff=lfs merge=lfs -text
6
+ *.ftz filter=lfs diff=lfs merge=lfs -text
7
+ *.gz filter=lfs diff=lfs merge=lfs -text
8
+ *.h5 filter=lfs diff=lfs merge=lfs -text
9
+ *.joblib filter=lfs diff=lfs merge=lfs -text
10
+ *.lfs.* filter=lfs diff=lfs merge=lfs -text
11
+ *.mlmodel filter=lfs diff=lfs merge=lfs -text
12
+ *.model filter=lfs diff=lfs merge=lfs -text
13
+ *.msgpack filter=lfs diff=lfs merge=lfs -text
14
+ *.npy filter=lfs diff=lfs merge=lfs -text
15
+ *.npz filter=lfs diff=lfs merge=lfs -text
16
+ *.onnx filter=lfs diff=lfs merge=lfs -text
17
+ *.ot filter=lfs diff=lfs merge=lfs -text
18
+ *.parquet filter=lfs diff=lfs merge=lfs -text
19
+ *.pb filter=lfs diff=lfs merge=lfs -text
20
+ *.pickle filter=lfs diff=lfs merge=lfs -text
21
+ *.pkl filter=lfs diff=lfs merge=lfs -text
22
+ *.pt filter=lfs diff=lfs merge=lfs -text
23
+ *.pth filter=lfs diff=lfs merge=lfs -text
24
+ *.rar filter=lfs diff=lfs merge=lfs -text
25
+ *.safetensors filter=lfs diff=lfs merge=lfs -text
26
+ saved_model/**/* filter=lfs diff=lfs merge=lfs -text
27
+ *.tar.* filter=lfs diff=lfs merge=lfs -text
28
+ *.tar filter=lfs diff=lfs merge=lfs -text
29
+ *.tflite filter=lfs diff=lfs merge=lfs -text
30
+ *.tgz filter=lfs diff=lfs merge=lfs -text
31
+ *.wasm filter=lfs diff=lfs merge=lfs -text
32
+ *.xz filter=lfs diff=lfs merge=lfs -text
33
+ *.zip filter=lfs diff=lfs merge=lfs -text
34
+ *.zst filter=lfs diff=lfs merge=lfs -text
35
+ *tfevents* filter=lfs diff=lfs merge=lfs -text