Slack Development Lessons - Part 1 Navigating Slack's Unique Development Environment

Harrison Strowd
Harrison Strowd

For the past six weeks, we've been dedicating our “20% time” to prototyping a Slack application that brings the functionality of Marginal directly to teams in Slack. After sketching out our vision for how users might interact with Marginal within Slack, we dove into technical discovery and pieced together a prototype. The goal? To uncover and mitigate potential risks while we explored what's possible with Slack's development tools.

This hands-on process taught us several valuable lessons that will shape the future development of a full-fledged version of this application. In this post, we'll cover three key takeaways from our experience, but there's also more to come in a subsequent post. So keep an eye out for Part 2, where we'll share additional lessons from this exercise.

1. Breaking Habits Is Hard (But Sometimes Necessary)

After spending decades refining good engineering habits, abandoning them—even temporarily—can feel counterintuitive. Practices like:


Prototyping requires loosening the reins on perfectionism. And that's okay.


…are second nature to engineers aiming to deliver high-quality, maintainable work. These habits are invaluable when building production-ready applications impacting thousands or even millions of users. However, when prototyping, these practices can slow you down. The goal of a prototype isn't to ship polished, scalable code but to quickly experiment, learn, and reduce risks.

While I knew these habits were unnecessary for this prototyping exercise, I still ended up falling back into them for the first half of the six week cycle we alloted for this work. With 3 weeks burned, I had only established the Marginal data model in the new backend service. While well-documented, covered by tests, and ready for production (if it existed), progress was slow. At this point I finally cut ties with these habits and started hacking through the remainder of the technical discovery work. Over the course of the next week, I experimented with all the Slack integrations we identified as unknown or high risk, including interactive messages, ephemeral posts, modals, and message threads.


This experience highlights the significant productivity cost (5-10x) of developing features robustly versus quickly hacking them together.


This experience highlights the significant productivity cost (5-10x) of developing features robustly versus quickly hacking them together. While this is certainly a high price to pay, in most cases it is a valuable investment in avoiding bugs, minimizing technical debt, and future engineers (i.e. your future self) from headaches while building on top of this work.

Lesson learned: Prototyping requires loosening the reins on perfectionism. And that's okay.

2. Limited Ruby Framework Support

Coming from the Rails community, we hoped to find a robust gem or Rails-like framework for building Slack apps in Ruby. Instead, we found a fairly sparse set of development tools available, with the Slack Ruby Bot Server standing out as the best option.

This server does a good job simplifying the Slack app setup operations (e.g., OAuth, event subscriptions) and handles core integrations like slash commands and interactive messages. There are also sample apps that provide helpful insights into using the framework for specific cases, such as consuming Slack events or integrating paid subscriptions with Stripe.


Ruby's Slack ecosystem is functional but far from plug-and-play. Be prepared for extra groundwork.


We greatly appreciated having the Slack Ruby Bot Server as a starting point to work from but for engineers coming from a Rails development environment, you may find some aspects of this framework more challenging than expected. In particular, we discovered:

One potential workaround is mounting the Ruby Slack Bot Server within a Rails app, as outlined in this article. This approach might allow us to leverage Rails' strengths while integrating Slack's functionality. It's something we'll explore further.

Lesson learned: Ruby's Slack ecosystem is functional but far from plug-and-play. Be prepared for extra groundwork.

3. Slack Is Not The Web

After years of building web applications, we've internalized many assumptions that don't carry over to Slack. For example:

In many cases these quirks require some rethinking of workflows and user experiences.


Slack's environment introduces unique challenges that demand creative solutions.


For example, our initial plan was to pop a modal when the Marginal App is added to a channel, allowing the user to quickly and easily provide all the information necessary to configure a series of Marginal discussions for this team. However, since there are multiple events that can result in an app being added into a channel, Slack does not allow modals to be triggered from this event. Instead, we had to post a message into the channel that prompts the user to provide the necessary information there.

Initially, this channel setup message included two dropdown input fields and a submit button. However, Slack's interactive messages don't operate like a web form where all information is collected in the client's browser and then submitted to the server in a single event. Instead, each interaction with a single element is delivered individually. We dropped the submit button altogether and implemented server-side logic to detect if all required inputs were complete.

This makes some cases far more challenging to distinguish and handle. For example, when a user interacts with one of the two dropdowns we presented, is this an indication that they didn't see or don't want to make a selection for the other dropdown? Or are they simply working their way through the series of inputs and just haven't reached that one yet?

These are just a few examples of how our web development paradigms had to shift to meet Slack’s requirements.

Lesson learned: Slack's environment introduces unique challenges that demand creative solutions.

Parting Thoughts and Next Steps

Prototyping our Slack app taught us invaluable lessons about adapting workflows, navigating Ruby's limited Slack ecosystem, and working within Slack's unique constraints. These insights will guide us in building the full-featured app and hopefully save us and others from headaches along the way.

Stay tuned for Part 2, where we'll dive into more lessons and takeaways from our Slack app development journey. In the meantime, have you worked on developing a Slack app? Are there other pitfalls we haven't encountered... yet? If so, we'd love to hear from you! Let us know your thoughts in the comments below.

Explore our writing

Our perspectives on engineering practices, sustainable business, and building technology with human connection at its core.

Leave a comment

Thoughts for our thoughts

We hope you find our writing useful and, perhaps, that it gives you something to think about. We read everything we receive and we'd love to hear from you.