3

I have a client-server system modelling an interactive business process with the following four constraints:-

  • The client may have stale data, and/or the client may be untrustworthy. All client-side commands must be validated on the server before their effects become "truth".

  • The client's user experience (though not normally the process itself) is sensitive to latency, the connection between the client and server is not reliable, and users need to be able to continue their workflow while outside of network range. The client must (to an extent) be able to update its own view of the state without making a round-trip to the server on every command - though the server may eventually reject those commands once communication is re-established.

  • The client and server hardware do not share a platform. My ability to share an implementation between client and server is severely limited.

  • The process is complicated, multi-step, and interactive - far out of scope of e.g. annotation-based validation frameworks.

My current intention is to build a system resembling the client-side prediction used in e.g. computer games. This necessitates building a "copy" of a sufficiently complete portion of the state of the system on the client, having the client evaluate commands against this cached copy of the state, and then synchronise those commands with the server as and when the connection is available.

To achieve this, it is necessary to essentially build the entire system - state, commands, rules, and events - twice. Once on the server platform, and once on the client platform.

I've come up against similar requirements previously, but never with all four of these constraints. I've always been able to either a) accept that the client might be untrustworthy, b) accept that the client must check-in with the server on every action, c) use the same implementation of the process on both client and server (e.g. shared binaries, or node), or d) coerce the model into something simple enough to use a validation framework.

I'm investigating transpiling, and also somehow invoking a compatible scripting environment from the server. While those investigations are ongoing, my initial conclusions are that doing so will be more challenging than maintaining two "copies" of the process.

Before I embark on this folly: are there any other strategies for interactive client-server processes that minimise the requirement for duplicate implementation?

  • What is the essential problem you're trying to solve here? Is the validation really so elaborate that you have to build a custom system just to handle it? My experience with such systems is that they need to be streamlined so that the validation is less onerous, not have additional software piled on top of them. – Robert Harvey Sep 4 '17 at 14:43
  • The actual validation of the state of any individual control (e.g. this text box can't be empty) isn't terribly elaborate. The validation of the commands (e.g. this actor can perform this action) on the server is. The process itself is interactive and multi-stage. A user may be working through several steps in their workflow without connection to the server. The client can't refer to the server to determine what the "next step" is, but the server must validate that the client made the correct decision vs its up-to-date copy of the state. – Iain Galloway Sep 4 '17 at 14:49
  • How much effort are we talking about, if you just write the client implement in the usual way? Does the server software already exist? What language/tools is it written in? What language/tools do you intend to write the client in? (Node.JS is Javascript on the client and the server). – Robert Harvey Sep 4 '17 at 14:52
  • If I was implementing the client as, say, a SPA+backend on a reasonable without meaningful "offline" functionality (option b, above), I'd be estimating on the order of some few person-months. The server software does not yet exist, but the client's backend team is .NET. The client is a javascript-like language running on proprietary hardware. My initial attempts to transpile a compatible language to run on the client devices are not promising, nor are our attempts to license a runtime that we can invoke from inside a .NET server process - though both options will be investigated. – Iain Galloway Sep 4 '17 at 14:56
  • 1
    @EmersonCardoso That's essentially what I think I'm going to end up doing - building an as-dumb-as-possible state machine on both the client and the server, and encoding (as far as possible) the process as data. – Iain Galloway Sep 13 '17 at 10:24
1

Based on your response to my comments, here goes my answer:

  • Fragment your business process into several small pieces
  • Use something like Xml or Json, or any other format, to describe each of these small pieces; you can store this in DB, and it can change over time;
  • You client and server code will actually be a parser of these data;
  • (optional) Since you have specific pieces already defined for your process, you could actually use the transpile approach in order to "generate" Parsers in different languages (eg: tomorrow you need to implement a iOS client, then you generate by transpiling an Objective-C parser code, for your process' small pieces)

I suggest this approach because I had to do something similar, and the process itself was frequently changed, by adding or removing steps. This approach helped a lot with development.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.