Locations
This guide covers how to create, organize, and manage locations in Tagnet. Locations represent the physical and logical places where inventory items are stored, moved through, and tracked: warehouses, zones, shelves, vehicles, staging areas, and more. The page's Types tab holds the location types that classify them.
Overview
Locations are organized in a hierarchical tree structure. A root location might represent a warehouse or building, with child locations for zones, aisles, shelves, or rooms beneath it. This hierarchy lets you model your facility layout at whatever level of detail you need.
| Use Case | Example Hierarchy |
|---|---|
| Warehouse | Warehouse → Zone A → Aisle 1 → Shelf 1 |
| Manufacturing | Plant → Production Line → Work Cell → Station |
| Field Assets | Region → District → Substation |
| IT Assets | Campus → Building → Floor → Room |
The Locations list is a single navigational tree: click any location to open its own page, which shows what's there now, how it has been trending, its floor plan, and its position on the map. From a location's page you can:
- Create and nest locations up to 11 levels deep
- Assign location types with icons and colors for visual identification
- Assign an optional Code to tie a location to your own external identifier
- Control which locations allow inventory assignment
- Move locations (and their children) to different parents
- View on-hand inventory, movement, and value for the location or its whole subtree
- Upload floor plans and map zones to child locations
- See the location on a map alongside the rest of its tree
Permissions
Location access is controlled by permissions assigned through roles:
| Permission | What It Allows |
|---|---|
| View Locations | See the location tree and open location pages |
| Manage Locations | Create, edit, move, copy, and delete locations |
Access scopes further control which locations a user can see and manage. Users only see locations belonging to their assigned scopes.
The Location Tree
The Locations page displays your hierarchy as a single expandable tree. Click a location's row anywhere in the tree to open its own page; the arrow at the start of the row is the only thing that expands it.
Tree Display
Each location row shows:
- Icon: Based on the location type, with color coding
- Name and description
- Code: The location's code (if set), shown next to the name
- Child count: A small ↳ icon and number next to locations that have children, showing how many rows expanding it will reveal
- On-hand summary: Once inventory stats finish loading, a compact quantity (and value, if unit costs are set) appears next to locations that hold inventory, either directly or across their subtree, for example "1.2k · $340K in subtree." Hover for exact figures.
- Floor plan icon: A Map icon appears (with View Floor Plans permission) when the location owns an active floor plan or is drawn as a zone on one; click it to open the floor plan viewer. See Floor Plans for the color coding and full details.
- Scope badge: Shown where the access scope changes from the parent (visible when multiple scopes are active)
- Actions menu (the ⋮ button at the end of the row): Edit, Copy, Add child, Move, and Delete, the same operations as the location page's Actions menu, so routine changes don't need a trip to the location first. Shown on locations you can manage (Manage Locations permission for the location's scope); each action returns you to the tree.
Search and Type Filter
Use the search bar to filter locations by name, code, type, or description, or open the filter drawer to narrow by Location Type. When a filter is active:
- Matching locations and their ancestors are shown so you can see context
- The tree automatically expands to reveal matches
- A summary shows how many locations match
Expand and Collapse
Click the arrow on any tree node to expand or collapse its children. Tagnet remembers which locations you left expanded, per user, so the tree reopens the way you left it, on any device; the first time, root locations start collapsed. While a search or filter is active the tree expands to show the matches instead. The Expand all and Collapse all buttons in the search bar open or close every level at once.
Creating a Location
Choose Location from the Add menu in the Locations page header to create a new root-level location, or click Add child on an existing location's page to create a location nested under it. Both open a full-page create form.
Availability
If you have access to more than one site scope, the create page asks which site scope owns the new location in an Availability section, right after Basics. It comes before Hierarchy because it decides which parent locations are available there: you can pick a parent from the chosen scope or from a shared (system-scope) location, but not from a different site.
If you only have access to one site scope, this section is skipped and that scope is used automatically. New locations are always created in a site scope: the system scope is not offered when creating a location. Locations that were placed in the system scope before this restriction keep working normally; they just can't be created that way going forward.
Location Fields
| Field | Description | Required |
|---|---|---|
| Name | Display name for the location | Yes |
| Code | Optional stable identifier that links this location to your external systems | No |
| Location type | Category that determines the icon and color | Yes |
| Inventory | Whether inventory items can be assigned here (Allowed or Not Allowed) | Yes |
| Description | Optional notes or details | No |
| Parent location | The parent in the hierarchy (shown when creating, not when editing). The whole Hierarchy section is hidden when there is no location it could sit under, such as your first location in a site | No |
| Latitude / Longitude | Optional coordinates for map display | No |
| Access Scope | Determines which users can see and manage this location (see Availability above) | Yes |
Inventory Strategy
The Inventory setting controls whether items can be assigned to this location:
| Strategy | When to Use |
|---|---|
| Allowed | Locations that directly hold inventory (shelves, bins, rooms) |
| Not Allowed | Organizational containers that group other locations (regions, buildings, zones) |
Setting a location to Not Allowed prevents items from being transacted to it directly, whether by a manual move, an API call, or a movement rule. Child locations can still allow inventory.
Note: A location that currently holds active inventory can't be switched to Not Allowed. Move or remove the items first; the field is disabled with an explanation until you do.
Location Code
The Code field is an optional, stable identifier you can use to tie a Tagnet location to a reference in your own systems. For example, a utility company might use pole numbers like 69A, a warehouse might use WMS location codes like WH1-A01-S03, or an IT department might use room identifiers like BLDG4:FL2:R214.
Unlike Name, which is a human-friendly label and does not need to be unique, a code must be unique within the location's access scope. Two locations can both be called "Receiving" but they cannot share the same code in the same scope. Locations in different access scopes can reuse the same code.
Formatting rules:
- Optional. Locations without a code still work normally; they are referenced by their internal numeric ID.
- Unique within the access scope, case-insensitive:
69aand69Aare treated as the same code and entering a duplicate in the same scope is rejected. - Stored and displayed in uppercase. You can type in lowercase; Tagnet uppercases it on save.
- Allowed characters: letters, digits, and the separators hyphen, underscore, dot, colon (
-_.:). No spaces or slashes. - Maximum 100 characters.
Codes are mutable. You can add a code to an existing location, correct a typo, or clear it by leaving the field blank. That said, treat renaming an established code like renaming a key: any external systems that stored the old value will stop finding the location by code and will need to be updated.
The form shows a live validation message if you enter invalid characters or a code that is already in use.
Display Format
Wherever a location appears as a chip (the Inventory and Transactions grids, item and transaction detail pages, location history, Live Reads, and dashboard widgets), you choose how it reads from Account > Profile > Location display format:
| Format | Chip shows | Hover shows |
|---|---|---|
| Name (default) | Row 3 | Site A > Yard > Row 3 |
| Full path | Site A > Yard > Row 3 | Nothing |
| Code | R3 | SITEA > YARD > R3 |
| Full code path | SITEA > YARD > R3 | Nothing |
| Scope + name | Site A · Row 3 | Site A > Yard > Row 3 |
| Scope + code | Site A · R3 | SITEA > YARD > R3 |
| Root + name | Site A · Row 3 | Site A > Yard > Row 3 |
| Root + code | SITEA · R3 | SITEA > YARD > R3 |
In the code formats, any location without a code shows its name instead, so a path always has one entry per level. The scope formats put the name of the location's access scope in front (including the shared scope), which helps when the same location names or codes repeat across sites. The root formats put the top-level location of the tree in front instead; a top-level location shows on its own. The preference is per user, applies everywhere at once, and persists across sessions. Global search results always show names, as does any location the page has not loaded (for example, a transaction location outside your access scopes).
Access Scope Rules
When creating a child location, scope inheritance follows these rules:
- Root locations (no parent) use the site scope chosen in Availability
- Children of a parent in a site scope must use the same scope as their parent, so the scope field is locked automatically
- Children of a parent in the system scope (only reachable on legacy locations) can use any site scope, chosen the same way as a root location
The form shows a lock icon and message when scope is inherited from the parent.
Depth Limit
Locations can be nested up to 11 levels deep (Level 1 through Level 11). The form warns you when approaching this limit.
Editing a Location
Click Edit on a location's page to modify its properties. You can change the name, code, type, description, inventory strategy, coordinates, and scope (if scope rules allow it). The parent location cannot be changed from the edit form; use Move instead.
Changing the access scope on a location with descendants moves the entire subtree to the new scope; you're asked to confirm before this happens.
The Location Page
Click any location to open its page (/locations/{id}). Breadcrumbs across the top show the full ancestor path, so you can move up the hierarchy from anywhere with one click. The page itself has four tabs.
Overview Tab
- Hero stats: Quantity here (or in subtree, for locations where inventory isn't allowed directly) and the 7-day movement trend. Each card is a link: quantity opens the Inventory list filtered to this location, and movement opens the matching Transactions.
- Basics: Location type, code (if set), inventory strategy, average time here (how long on-hand inventory has been at this location, on average; average time in subtree for locations where inventory isn't allowed directly), coordinates (if set), description
- Sublocations: Everything below this location, as the same tree as the Locations page with this location's children at the top. Expand a row's arrow to see the levels beneath it in place, without opening each location in turn; click a row to open that location's own page. The header shows how many direct children and how many locations in total sit below, with Expand all / Collapse all and Add child. Rows carry the same ⋮ actions menu as the Locations page, and expansion is shared with it: a location you keep open there is open here too.
- Devices here: The devices whose read point is this location, set on the device itself or on its group
- Audit information: Created and updated timestamps and users
From the Actions menu in the page header you can Edit, Copy, Add child, Move, or Delete the location (if you have Manage Locations permission for its scope). For a location that allows inventory, the menu starts with Add inventory here (with Edit Inventory permission), which opens the inventory form with this location filled in. To see what is here, click the Quantity card: it opens the Inventory list filtered to this location.
Analytics Tab
Shows how the inventory at this location has been changing and moving: the charts from the location's inventory slice, the view you get at /inventory/location/{id} under the Inventory page.
For locations that allow inventory directly, a lens toggle lets you switch between Include sublocations (the default) and This location only. Locations where inventory isn't allowed directly (organizational containers) always show the subtree, since nothing can be on hand at the node itself.
- Inventory level: A time series chart of on-hand quantity over the selected range (24h/7d/30d/90d). The range toggle in this chart's header drives both charts.
- Movement: A time series chart broken down by transaction type over the same range
The tab shows charts only, since the Overview already carries the figures. The value total and the breakdown tables (on-hand quantity and value by sublocation, and by item or item type) are on the location's slice page at /inventory/location/{id}.
Floor Plan Tab
Shown to users with View Floor Plans permission. It opens view-first: an interactive pan/zoom viewer where clicking a zone shows a details popup with that location's inventory summary. If you have Manage Floor Plans permission, an Edit floor plan button switches to the zone editor; Done editing returns you to the viewer.
If the location is covered by another location's floor plan instead (mapped as a zone, whether an ancestor's or a shared plan) but has no plan of its own, the tab shows that plan read-only with this location's zone highlighted, along with a link to open the owning location and, if you have Manage Floor Plans permission, a button to upload a plan of this location's own.
See the Floor Plans guide for full details on uploading plans, drawing and styling zones, and reading the zone details popup.
Map Tab
Shown only when at least one location in this location's tree has coordinates set. Plots every coordinate-bearing location in the whole tree (not just this location's descendants) on an interactive map, with this location's pin enlarged and focused. Click a pin's popup to navigate to that location's own page.
Moving a Location
Moving lets you change a location's parent, relocating it (and all its descendants) to a different spot in the hierarchy. Click Move on a location's page to open the move form.
How It Works
- The page shows the location's current path in the hierarchy
- Select a new parent using the tree selector, or choose Root Level (No Parent) to make it a top-level location
- An impact preview shows what will happen before you confirm:
- Descendant count: How many child locations will move along
- Scope change: Whether the access scope will change, and for how many locations
- Confirm to complete the move
What Happens When You Move
- The location and all its descendants move together to the new parent
- Hierarchy levels are recalculated automatically for the entire subtree
- If the new parent has a site scope that differs from the current scope, the scope is updated for the location and all its descendants
Validation
The system prevents moves that would:
- Create a circular reference (moving a location under one of its own descendants)
- Exceed the maximum depth limit of 11 levels, accounting for the full subtree depth
Scope Cascading on Move
When moving under a parent with a site scope:
| Scenario | Result |
|---|---|
| New parent has same scope as the location | No scope change |
| New parent has a different site scope | Scope updates for the location and all descendants |
| New parent has the system scope (legacy locations only) | Scope is preserved |
| Moving to root level (no parent) | Scope is preserved |
Copying a Location
Copying lets you create a new location with the same setup as an existing one, without re-entering every field by hand. Click Copy on a location's page to open the copy form. The button sits in the action row alongside Edit, Add child, Move, and Delete, and is available to users with Manage Locations permission for the location's scope.
How It Works
Copy opens the Create Location page in copy mode, titled Copy Location, with the following fields prefilled from the source location:
- Location type
- Description
- Parent location
- Access scope
- Inventory setting
- Latitude / longitude
The Name is prefilled as "Source Name (Copy)" so the new location is easy to tell apart from the original at a glance.
The Code is left blank. Codes must be unique within an access scope, so the source location's code can't be reused; enter a new one, or leave it blank if your locations don't require a code.
You can adjust any field before saving. Saving creates a new, independent location: child locations, floor plans, and inventory are not copied along with it.
Deleting a Location
Open the Actions menu on the location's page, or on the location's row in the tree, and select Delete.
Before asking you to confirm, Tagnet checks everything that blocks the delete. If anything does, the dialog lists every blocker, each with its count and what to do about it, and offers only Close. Nothing is deleted, and you can clear all the blockers in one pass instead of discovering them one at a time. If nothing blocks the delete, the dialog asks you to confirm with Delete.
A location cannot be deleted while any of these apply:
| Blocker | What to do |
|---|---|
| It has child locations | Delete or move the children first |
| It has inventory transaction history | The location stays, to keep that history. Set its Inventory to Not Allowed instead, so nothing new is stored there |
| Items are currently at the location | Move the items or close them out first (see Inventory) |
| It has a floor plan | Delete the floor plan first (see Floor Plans) |
| It is placed as a zone on a floor plan | Remove the zone from that floor plan first |
| It is the read point location of devices or device groups | Clear the read point location on those devices and groups first (see Read Point Location) |
Inventory level snapshots do not block a delete. They are derived summaries, so Tagnet removes them along with the location.
If something changes between the check and the delete (for example, another user moves an item to the location), Tagnet refuses the delete and shows a message. Open Delete again to see the current blockers.
Floor Plans
Locations can have PDF floor plans that provide a visual map of your facility, managed from the location's own Floor plan tab. Floor plans connect the location hierarchy to a spatial layout: you upload a plan to a parent location and draw zones linked to child locations.
For full details on uploading, drawing zones, and viewing floor plans, see the Floor Plans guide.
Location Types
Each location is assigned a type that determines its icon and color in the tree. Location types are managed separately by administrators and help visually distinguish different kinds of locations (warehouses, rooms, vehicles, bins, etc.).
For Integrations
If you connect Tagnet to an external system (ERP, WMS, or a custom tool), location codes give you a stable way to reference locations without relying on Tagnet's internal numeric IDs.
Look up a location by code
GET /api/v1/locations/by-code/{code}
Returns the full location record for the given code. Useful when your system knows the code (e.g., the WMS location ID) and needs to get Tagnet's details or ID.
Codes are unique within an access scope, not across the whole system. If the same code is visible to you in more than one scope, add ?scope= with the access scope code to say which one you mean. Integrations that work within a single scope never need this.
Create or update a location by code (upsert)
PUT /api/v1/locations/by-code/{code}
If a location with that code already exists, Tagnet updates it with the fields you provide. If it does not exist, Tagnet creates it. This is the recommended pattern for "ensure this location exists" provisioning from an external system: run it repeatedly without worrying about duplicates.
The upsert key is the combination of access scope and code. Include scope in the request body to target a specific scope; without it, Tagnet uses your credential's scope. If the code exists in several scopes you can see, the request is rejected until you specify scope.
Note: The parent cannot be changed via upsert. To move a location to a different parent, use
POST /api/v1/locations/{id}/move.
Build a location hierarchy using codes as parent references
When creating or upserting locations, you can reference the parent location by code instead of by numeric ID:
{
"name": "Shelf 1",
"parentLocationCode": "WH1-A01"
}
This lets you provision an entire location tree top-down using only codes from your own system, with no need to capture Tagnet's internal IDs at any step.
Because codes are unique per access scope, the parent code is looked up in the scope you supply (and then in the System scope, since a site location may sit under a System parent). Without scope, a parent code that exists in more than one scope you can see is rejected; supply scope or use parentLocationId instead.
Best Practices
- Model your physical layout: Create a hierarchy that mirrors how your facilities are actually organized. This makes it intuitive for field users to find locations.
- Use inventory strategy intentionally: Set organizational groupings (regions, buildings) to Not Allowed so items can only be assigned to the leaf-level locations where they actually reside.
- Keep depth manageable: While the system supports up to 11 levels, most facilities work well with 3–5 levels of nesting.
- Use location types consistently: Assign meaningful types to make the tree visually scannable. For example, use "Warehouse" for buildings, "Zone" for areas, and "Shelf" for storage units.
- Assign codes where you integrate: If an external system (ERP, WMS, asset register) already has identifiers for your locations, set those as codes in Tagnet. You can then look up and provision locations by code without tracking Tagnet's internal IDs.
- Treat code renames carefully: Once an external system has stored a location code, changing it breaks any lookup that relied on the old value. Establish a naming convention early and communicate any renames to integration owners.
- Use each location's Analytics tab for stock reviews: Check the on-hand and movement trends for a warehouse or zone before deciding whether to rebalance inventory across sites.
- Plan your scope structure: Decide on your access scope strategy before creating locations. Moving locations between scopes later is possible but affects all descendants.
- Use floor plans for spatial context: Upload floor plans for key locations and map zones to give your team a visual reference for where things are.
FAQ
Do I have to assign a code to every location? No. Codes are optional. Locations without a code work exactly the same as those with one; they are just referenced by their internal numeric ID instead of a stable code. Codes are most useful when you are integrating Tagnet with another system that already has its own identifiers for the same locations.
Can two locations have the same code? Only if they are in different access scopes. Codes are unique within a scope, so two sites can each have their own location with the same code (useful when both sites mirror the same external system identifiers). Within one scope, entering a code that is already in use shows a validation error before you can save.
I typed a lowercase code but it saved as uppercase. Is that expected?
Yes. Tagnet normalizes codes to uppercase on save so that uniqueness is enforced consistently regardless of how the code was entered. shelf-01 and SHELF-01 are the same code.
Can I change a location's code after it has been set? Yes. You can update, rename, or clear a code at any time from the Edit page. If external systems have stored the old code, they will not find the location by code until you update those systems to use the new value.
Can I change a location's parent? Yes, use the Move action. This is separate from Edit because moving has cascading effects on children and potentially on access scopes.
What happens to inventory items when I move a location? Items stay assigned to the same location. Only the location's position in the hierarchy changes; the items move with it.
Can I move a location to a different access scope? If the new parent has a site scope, the location and all its descendants will automatically adopt that scope. If the new parent is in the system scope or is root-level, the existing scope is preserved.
Why can't I create a new location in the system scope? Locations are always created in a site scope now, so the new-location form only offers site scopes. This keeps every new location clearly owned by a site. If you have older locations that were placed in the system scope before this change, they continue to work; the restriction only applies to new locations going forward.
Why can't I switch a location's Inventory setting to Not Allowed? This location currently holds active inventory. Move or close out the items first (see Inventory); the field re-enables once the location is empty.
Why did my movement rule or Move Inventory action fail to place an item? The destination location it resolved to has Inventory set to Not Allowed. Every placement path, manual moves, the API, movement rules, and the Move Inventory workflow action, requires the destination to allow inventory.
What you see depends on which path ran:
- Move Inventory action: the tags are skipped, not failed. Each tag row in the execution names the location that cannot hold inventory and what to change, and the action reports no effect instead of an error. This is the normal result when a device sits at an organizational container such as a site root.
- Movement rules: the tags are reported as errors on the rule's result.
The fix is the same either way: point the rule or action at a location that allows inventory, or change the location's Inventory setting if it should hold items.
Why can't I delete a location? Select Delete from the Actions menu and Tagnet lists everything in the way, with a count and a fix for each. The blockers are child locations, inventory transaction history, items currently at the location, a floor plan on the location, placement as a zone on a floor plan, and being the read point location of a device or device group. If the location has transaction history, it stays to keep that history; set its Inventory to Not Allowed so nothing new is stored there. See Deleting a Location for the full list.
Why is the scope field locked when creating a child location? If the parent has a site scope, child locations must share that scope. This ensures scope consistency within a branch of the hierarchy.