|
3 | 3 |
|
4 | 4 | ## Protocol generation |
5 | 5 |
|
6 | | -Protocol is auto-generated from the "protocol" directory, from "common" and "pulse" subdirs. |
| 6 | +Protocol C# files are auto-generated from the sibling [protocol](https://github.com/decentraland/protocol/tree/quantization) repo using `protoc` + the `protoc-gen-bitwise` plugin. |
7 | 7 |
|
8 | | -It should reside on the same level as the root of the repo. You can modify `Directory.Build.props` to point to another location. |
| 8 | +### Prerequisites |
9 | 9 |
|
10 | | -The protocol branch should start off from "quantization" branch https://github.com/decentraland/protocol/tree/quantization. |
| 10 | +The `protocol` repo must be checked out as a sibling of this repo: |
| 11 | + |
| 12 | +``` |
| 13 | +D:\<root>\protocol\ ← @dcl/protocol (quantization branch) |
| 14 | +D:\<root>\Pulse\ ← this repo |
| 15 | +``` |
| 16 | + |
| 17 | +You can override the path via `Directory.Build.props` or `-p:_ProtocolRepo=<path>`. |
| 18 | + |
| 19 | +### GenerateProto switch |
| 20 | + |
| 21 | +The `Protocol.csproj` has a `GenerateProto` property that controls whether `.proto` files are regenerated at build time or the committed `Generated/` files are used as-is. |
| 22 | + |
| 23 | +| Mode | When to use | What happens | |
| 24 | +|------|------------|--------------| |
| 25 | +| `GenerateProto=true` (default) | Local development with the `protocol` repo available | Runs `protoc` + bitwise plugin, regenerates `src/Protocol/Generated/` | |
| 26 | +| `GenerateProto=false` | Docker builds, CI, or when the `protocol` repo is not available | Skips generation, compiles committed `Generated/*.cs` files directly | |
| 27 | + |
| 28 | +To build without generation: |
| 29 | + |
| 30 | +```bash |
| 31 | +dotnet build -p:GenerateProto=false |
| 32 | +``` |
| 33 | + |
| 34 | +After modifying `.proto` files, build normally (or explicitly with `GenerateProto=true`) and commit the updated `Generated/` files so Docker and CI builds stay in sync. |
| 35 | + |
| 36 | +#### Rider |
| 37 | + |
| 38 | +To set `GenerateProto` from Rider: |
| 39 | + |
| 40 | +- **Solution-wide:** Settings → Build, Execution, Deployment → Toolset and Build → MSBuild CLI arguments → add `-p:GenerateProto=false` |
| 41 | +- **Per configuration:** Run → Edit Configurations → select configuration → Before launch → click the build step → add `-p:GenerateProto=false` to MSBuild arguments |
| 42 | + |
| 43 | +In practice the default (`true`) is correct for local development. The `false` value is used by Docker/CI builds that don't have the protocol repo available. |
| 44 | + |
| 45 | +## Docker debugging |
| 46 | + |
| 47 | +### Start the debug container |
| 48 | + |
| 49 | +```bash |
| 50 | +docker compose -f docker-compose.debug.yml up --build |
| 51 | +``` |
| 52 | + |
| 53 | +Wait for the server to log that it is listening on port 7777. The `src/` directory is volume-mounted — after editing source, restart the container to pick up changes (`docker compose -f docker-compose.debug.yml restart`). |
| 54 | + |
| 55 | +### Attach Rider |
| 56 | + |
| 57 | +1. Run → Edit Configurations → **+** → **.NET Attach to Remote Process** |
| 58 | +2. Connection type: **Docker container** |
| 59 | +3. Container: `dcl-pulse-debug` |
| 60 | +4. vsdbg path: `/vsdbg` |
| 61 | +5. Path mapping: local `./src` ↔ container `/app/src` (usually resolved automatically via the volume mount; set manually if Rider misses it) |
| 62 | + |
| 63 | +Use **logpoints over breakpoints** for networking code (right-click gutter → Add Logpoint). They log to the Debug console without pausing the ENet tick loop or disconnecting clients. |
| 64 | + |
| 65 | +### Quick reference |
| 66 | + |
| 67 | +| Action | Command | |
| 68 | +|---|---| |
| 69 | +| Start | `docker compose -f docker-compose.debug.yml up --build` | |
| 70 | +| Tail logs | `docker logs -f dcl-pulse-debug` | |
| 71 | +| Rebuild | `docker compose -f docker-compose.debug.yml up --build --force-recreate` | |
| 72 | +| Stop | `docker compose -f docker-compose.debug.yml down` | |
| 73 | +| Connect client | `127.0.0.1:7777` | |
| 74 | + |
| 75 | +### Remote debugging (dev environment) |
| 76 | + |
| 77 | +The **Deploy Dev (Debug)** workflow (`deploy-dev-debug.yml`) deploys a debug-capable image to the dev environment. Trigger it manually from the GitHub Actions UI. |
| 78 | + |
| 79 | +The debug image includes vsdbg and full debug symbols but runs on the slim `dotnet/runtime` base (not the SDK), so it's close to production weight. |
| 80 | + |
| 81 | +#### Connecting Rider via ECS Exec |
| 82 | + |
| 83 | +1. Find the running task: |
| 84 | + |
| 85 | +```bash |
| 86 | +aws ecs list-tasks --cluster <cluster> --service-name dcl-pulse --query 'taskArns[0]' --output text |
| 87 | +``` |
| 88 | + |
| 89 | +2. Verify ECS Exec is enabled and attach: |
| 90 | + |
| 91 | +```bash |
| 92 | +aws ecs execute-command \ |
| 93 | + --cluster <cluster> \ |
| 94 | + --task <task-id> \ |
| 95 | + --container dcl-pulse \ |
| 96 | + --interactive \ |
| 97 | + --command "/bin/bash" |
| 98 | +``` |
| 99 | + |
| 100 | +3. In Rider: Run → Edit Configurations → **+** → **.NET Attach to Remote Process** |
| 101 | + - Connection type: **Custom pipe** |
| 102 | + - Pipe command: `aws ecs execute-command --cluster <cluster> --task <task-id> --container dcl-pulse --interactive --command` |
| 103 | + - Debugger path: `/vsdbg/vsdbg` |
| 104 | + - Path mapping: local `src/` ↔ container `/app/` |
| 105 | + |
| 106 | +4. Select the `dotnet` process from the process list. |
| 107 | + |
| 108 | +Prefer **logpoints over breakpoints** — a breakpoint pauses the ENet tick loop and disconnects all clients. |
| 109 | + |
| 110 | +#### Reverting to production |
| 111 | + |
| 112 | +After debugging, push to `main` or run the **Manual Deploy** workflow to redeploy the production image. |
0 commit comments