Deploy AIOS web (React glide grid + FastAPI slice)
Browse files- RELEASES.json +7 -1
- VERSION +1 -1
- web/src/customer-grid/CustomerGrid.tsx +18 -3
RELEASES.json
CHANGED
|
@@ -1,6 +1,12 @@
|
|
| 1 |
{
|
| 2 |
-
"current": "
|
| 3 |
"releases": [
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 4 |
{
|
| 5 |
"version": "v35",
|
| 6 |
"sha": "0f64212",
|
|
|
|
| 1 |
{
|
| 2 |
+
"current": "v36 (51db3b7)",
|
| 3 |
"releases": [
|
| 4 |
+
{
|
| 5 |
+
"version": "v36",
|
| 6 |
+
"sha": "51db3b7",
|
| 7 |
+
"date": "2026-08-21",
|
| 8 |
+
"subject": "W39 share-field oid repair"
|
| 9 |
+
},
|
| 10 |
{
|
| 11 |
"version": "v35",
|
| 12 |
"sha": "0f64212",
|
VERSION
CHANGED
|
@@ -1 +1 @@
|
|
| 1 |
-
|
|
|
|
| 1 |
+
v36 (51db3b7)
|
web/src/customer-grid/CustomerGrid.tsx
CHANGED
|
@@ -224,6 +224,21 @@ const ROW_PX: Record<RowHeightMode, number> = { short: 28, medium: 34, tall: 48
|
|
| 224 |
const DIRECTIONS_COLUMN_ID = "__directions__";
|
| 225 |
const DIRECTIONS_COLUMN: GridColumn = { id: DIRECTIONS_COLUMN_ID, title: "Go", width: 46 };
|
| 226 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 227 |
/** `null` means there is no honest Google destination, including a blank-address row. */
|
| 228 |
function directionsFor(row: Row): { lat: number; lon: number } | null {
|
| 229 |
const lat = row.lat;
|
|
@@ -7896,12 +7911,12 @@ function CustomerGridSurface({
|
|
| 7896 |
`core.shares.split_field_oid` fails closed on an id it cannot resolve,
|
| 7897 |
`routes_shares._object_ref` answers `route=None`, and `_notify_new_grantees` returns
|
| 7898 |
early — the grant lands and the receiver is NEVER TOLD. So this reads the SERVER's
|
| 7899 |
-
|
| 7900 |
-
|
| 7901 |
⚠ Only this instance takes it. The "+" render below opens straight into the create
|
| 7902 |
form and never paints the action list, so the row it feeds is unreachable there —
|
| 7903 |
unlike `linkTargets`, which both create paths genuinely need. */
|
| 7904 |
-
tableKey={
|
| 7905 |
/>
|
| 7906 |
)}
|
| 7907 |
|
|
|
|
| 224 |
const DIRECTIONS_COLUMN_ID = "__directions__";
|
| 225 |
const DIRECTIONS_COLUMN: GridColumn = { id: DIRECTIONS_COLUMN_ID, title: "Go", width: 46 };
|
| 226 |
|
| 227 |
+
/**
|
| 228 |
+
* The table half of a field-share oid. A workspace `storageKey` is deliberately
|
| 229 |
+
* per-tenant and per-user (`qa-b:ut_…:qa-runner`); it is a persistence bucket,
|
| 230 |
+
* not the database identifier `core.shares.split_field_oid` can resolve.
|
| 231 |
+
*/
|
| 232 |
+
export function fieldShareTableKey(
|
| 233 |
+
scope: SurfaceScope,
|
| 234 |
+
isQueryPreview: boolean,
|
| 235 |
+
): string | undefined {
|
| 236 |
+
if (isQueryPreview) return undefined;
|
| 237 |
+
if (scope === "customer" || scope === "cohort") return "customer_data";
|
| 238 |
+
if (scope === "product") return "product_data";
|
| 239 |
+
return scope.startsWith("ut_") ? scope : undefined;
|
| 240 |
+
}
|
| 241 |
+
|
| 242 |
/** `null` means there is no honest Google destination, including a blank-address row. */
|
| 243 |
function directionsFor(row: Row): { lat: number; lon: number } | null {
|
| 244 |
const lat = row.lat;
|
|
|
|
| 7911 |
`core.shares.split_field_oid` fails closed on an id it cannot resolve,
|
| 7912 |
`routes_shares._object_ref` answers `route=None`, and `_notify_new_grantees` returns
|
| 7913 |
early — the grant lands and the receiver is NEVER TOLD. So this reads the SERVER's
|
| 7914 |
+
logical database key rather than `workspace.storageKey`, and hides the Share row
|
| 7915 |
+
where the scope has no shareable table.
|
| 7916 |
⚠ Only this instance takes it. The "+" render below opens straight into the create
|
| 7917 |
form and never paints the action list, so the row it feeds is unreachable there —
|
| 7918 |
unlike `linkTargets`, which both create paths genuinely need. */
|
| 7919 |
+
tableKey={fieldShareTableKey(scope, isQueryPreview)}
|
| 7920 |
/>
|
| 7921 |
)}
|
| 7922 |
|