Skip to content

Commit

Permalink
MAK-62 IJ: Action to start/stop breaks (#105)
Browse files Browse the repository at this point in the history
  • Loading branch information
bcosynot authored Jul 10, 2023
1 parent 62228fd commit d1f4595
Show file tree
Hide file tree
Showing 21 changed files with 729 additions and 164 deletions.
26 changes: 18 additions & 8 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -12,18 +12,28 @@ track of all your notifications.
### Added

- Initial release!
- Added a status bar widget and action to toggle Flow Mode
- Block distracting websites with the Makerflow browser extension
- Turn on Do-Not-Disturb mode on macOS
- Update your status on Slack to let your team know you're in Flow Mode
- Start a timer to track your flow time
- Close distracting apps with the Makerflow desktop app
- Added a tool window to see items in Unified Task List
- Flow Mode allows you to:
- Block Interruptions & Distractions to focus on the task at hand, by suppressing notifications and blocking distracting websites or apps
- Easily start and stop Flow Mode from anywhere in your IDE by searching for `Flow Mode` in "Search Everywhere" (double shift in default keymap)
- Start, stop, and track your flow time in the status bar
- Updates your status on Slack automatically to let your team know you're in Flow Mode
- Automatically
- Starts Flow Mode if you have been coding for some time
- block distracting websites while in Flow Mode (requires Makerflow browser extension)
- Turn on Do-Not-Disturb mode on macOS when in Flow Mode (requires Makerflow desktop app)
- Close distracting apps like Slack and Discord when in Flow Mode (requires Makerflow desktop app)
- Unified Task List tool window lets you:
- See all your notifications from GitHub/Bitbucket in your IDE
- Add new tasks
- Start Flow Mode for a task to focus on it
- Added a tool window to see your calendar events for the next few hours
- A tool window to see your calendar events for the next few hours
- Join an upcoming event with one click
- Take breaks
- Easily from anywhere in the IDE by searching for `Begin break` in "Search Everywhere" (double shift in default keymap)
- Or from the status bar
- Makerflow will automatically update your Slack status to let your team know you're on a break
- Choose from a list of activities to do during your break like brewing coffee, going for a walk, grabbing lunch and other common activities
- Track your break time in the status bar

### Changed

Expand Down
152 changes: 81 additions & 71 deletions src/main/kotlin/co/makerflow/client/apis/BreaksApi.kt
Original file line number Diff line number Diff line change
Expand Up @@ -15,123 +15,133 @@

package co.makerflow.client.apis

import co.makerflow.client.infrastructure.ApiClient
import co.makerflow.client.infrastructure.HttpResponse
import co.makerflow.client.infrastructure.RequestConfig
import co.makerflow.client.infrastructure.RequestMethod
import co.makerflow.client.infrastructure.wrap
import co.makerflow.client.models.BreakReason
import co.makerflow.client.models.EndedWorkBreak
import co.makerflow.client.models.WorkBreak

import co.makerflow.client.infrastructure.*
import com.fasterxml.jackson.databind.ObjectMapper
import io.ktor.client.HttpClientConfig
import io.ktor.client.request.forms.formData
import io.ktor.client.engine.HttpClientEngine
import io.ktor.http.ParametersBuilder
import com.fasterxml.jackson.databind.ObjectMapper

open class BreaksApi(
open class BreaksApi(
baseUrl: String = ApiClient.BASE_URL,
httpClientEngine: HttpClientEngine? = null,
httpClientConfig: ((HttpClientConfig<*>) -> Unit)? = null,
jsonBlock: ObjectMapper.() -> Unit = ApiClient.JSON_DEFAULT,
) : ApiClient(baseUrl, httpClientEngine, httpClientConfig, jsonBlock) {
) : ApiClient(baseUrl, httpClientEngine, httpClientConfig, jsonBlock) {

/**
*
*
* @param source To specify source of request (optional)
* @return WorkBreak
*/
@Suppress("UNCHECKED_CAST")
open suspend fun getOngoingBreak(source: kotlin.String?): HttpResponse<WorkBreak> {
/**
*
*
* @param source To specify source of request (optional)
* @return WorkBreak
*/
@Suppress("UNCHECKED_CAST")
open suspend fun getOngoingBreak(source: kotlin.String?): HttpResponse<WorkBreak> {

val localVariableAuthNames = listOf<String>("api_token")
val localVariableAuthNames = listOf<String>("api_token")

val localVariableBody =
io.ktor.client.utils.EmptyContent
val localVariableBody =
io.ktor.client.utils.EmptyContent

val localVariableQuery = mutableMapOf<String, List<String>>()
source?.apply { localVariableQuery["source"] = listOf("$source") }
val localVariableQuery = mutableMapOf<String, List<String>>()
source?.apply { localVariableQuery["source"] = listOf("$source") }

val localVariableHeaders = mutableMapOf<String, String>()
val localVariableHeaders = mutableMapOf<String, String>()

val localVariableConfig = RequestConfig<kotlin.Any?>(
val localVariableConfig = RequestConfig<kotlin.Any?>(
RequestMethod.GET,
"/work-break/ongoing",
query = localVariableQuery,
headers = localVariableHeaders,
requiresAuthentication = true,
)
)

return request(
return request(
localVariableConfig,
localVariableBody,
localVariableAuthNames
).wrap()
}

/**
*
*
* @param source To specify source of request (optional)
* @return WorkBreak
*/
@Suppress("UNCHECKED_CAST")
open suspend fun startWorkBreak(source: kotlin.String?): HttpResponse<WorkBreak> {

val localVariableAuthNames = listOf<String>("api_token")

val localVariableBody =
io.ktor.client.utils.EmptyContent

val localVariableQuery = mutableMapOf<String, List<String>>()
source?.apply { localVariableQuery["source"] = listOf("$source") }

val localVariableHeaders = mutableMapOf<String, String>()

val localVariableConfig = RequestConfig<kotlin.Any?>(
).wrap()
}

/**
*
*
* @param reason Reason for the break
* @param source To specify source of request (optional)
* @param workdayId (optional)
* @return WorkBreak
*/
@Suppress("UNCHECKED_CAST")
open suspend fun startWorkBreak(
reason: BreakReason,
source: kotlin.String?,
workdayId: kotlin.Int?
): HttpResponse<WorkBreak> {

val localVariableAuthNames = listOf<String>("api_token")

val localVariableBody =
io.ktor.client.utils.EmptyContent

val localVariableQuery = mutableMapOf<String, List<String>>()
source?.apply { localVariableQuery["source"] = listOf("$source") }
reason?.apply { localVariableQuery["reason"] = listOf(reason.name.lowercase()) }
workdayId?.apply { localVariableQuery["workdayId"] = listOf("$workdayId") }

val localVariableHeaders = mutableMapOf<String, String>()

val localVariableConfig = RequestConfig<kotlin.Any?>(
RequestMethod.POST,
"/work-break/start",
query = localVariableQuery,
headers = localVariableHeaders,
requiresAuthentication = true,
)
)

return request(
return request(
localVariableConfig,
localVariableBody,
localVariableAuthNames
).wrap()
}
).wrap()
}

/**
*
*
* @param source To specify source of request (optional)
* @return EndedWorkBreak
*/
@Suppress("UNCHECKED_CAST")
open suspend fun stopOngoingBeak(source: kotlin.String?): HttpResponse<EndedWorkBreak> {
/**
*
*
* @param source To specify source of request (optional)
* @return EndedWorkBreak
*/
@Suppress("UNCHECKED_CAST")
open suspend fun stopOngoingBeak(source: kotlin.String?): HttpResponse<EndedWorkBreak> {

val localVariableAuthNames = listOf<String>("api_token")
val localVariableAuthNames = listOf<String>("api_token")

val localVariableBody =
io.ktor.client.utils.EmptyContent
val localVariableBody =
io.ktor.client.utils.EmptyContent

val localVariableQuery = mutableMapOf<String, List<String>>()
source?.apply { localVariableQuery["source"] = listOf("$source") }
val localVariableQuery = mutableMapOf<String, List<String>>()
source?.apply { localVariableQuery["source"] = listOf("$source") }

val localVariableHeaders = mutableMapOf<String, String>()
val localVariableHeaders = mutableMapOf<String, String>()

val localVariableConfig = RequestConfig<kotlin.Any?>(
val localVariableConfig = RequestConfig<kotlin.Any?>(
RequestMethod.POST,
"/work-break/stop",
query = localVariableQuery,
headers = localVariableHeaders,
requiresAuthentication = true,
)
)

return request(
return request(
localVariableConfig,
localVariableBody,
localVariableAuthNames
).wrap()
}
).wrap()
}

}
}
21 changes: 21 additions & 0 deletions src/main/kotlin/co/makerflow/client/models/BreakReason.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
package co.makerflow.client.models


/**
* Reason for a break during the workday.
*
* Can be one of the following:
* - coffee
* - tea
* - beverage
* - walk
* - lunch
* - running
* - workout
* - doctor
* - child
* - other
*/
enum class BreakReason {
COFFEE, TEA, BEVERAGE, WALK, LUNCH, RUNNING, WORKOUT, DOCTOR, CHILD, OTHER;
}
8 changes: 5 additions & 3 deletions src/main/kotlin/co/makerflow/client/models/EndedWorkBreak.kt
Original file line number Diff line number Diff line change
Expand Up @@ -16,20 +16,22 @@
package co.makerflow.client.models


import com.fasterxml.jackson.annotation.JsonIgnoreProperties
import com.fasterxml.jackson.annotation.JsonProperty

/**
* Objet represent a break from work that has ended
*
* @param id
* @param userId
* @param id
* @param userId
* @param start Timestamp for when the break was started
* @param end Timestamp for when the break was ended
* @param reason Reason for taking the break
*/


data class EndedWorkBreak (
@JsonIgnoreProperties(ignoreUnknown = true)
data class EndedWorkBreak(

@field:JsonProperty("id")
val id: kotlin.Int,
Expand Down
8 changes: 5 additions & 3 deletions src/main/kotlin/co/makerflow/client/models/WorkBreak.kt
Original file line number Diff line number Diff line change
Expand Up @@ -16,20 +16,22 @@
package co.makerflow.client.models


import com.fasterxml.jackson.annotation.JsonIgnoreProperties
import com.fasterxml.jackson.annotation.JsonProperty

/**
* Object representing a break from work
*
* @param id
* @param userId
* @param id
* @param userId
* @param start Timestamp for when the break was started
* @param reason Reason for taking the break
* @param end Timestamp for when the break was ended
*/


data class WorkBreak (
@JsonIgnoreProperties(ignoreUnknown = true)
data class WorkBreak(

@field:JsonProperty("id")
val id: kotlin.Int,
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,69 @@
package co.makerflow.intellijplugin.actions

import co.makerflow.intellijplugin.dialogs.StartWorkBreakDialog
import co.makerflow.intellijplugin.services.WorkBreakService
import co.makerflow.intellijplugin.state.FlowState
import co.makerflow.intellijplugin.state.WorkBreakState
import co.makerflow.intellijplugin.state.WorkBreakStateChangeNotifier
import com.intellij.icons.AllIcons
import com.intellij.openapi.actionSystem.ActionUpdateThread
import com.intellij.openapi.actionSystem.AnAction
import com.intellij.openapi.actionSystem.AnActionEvent
import com.intellij.openapi.actionSystem.DataContext
import com.intellij.openapi.application.ApplicationManager
import com.intellij.openapi.components.service
import com.intellij.util.ui.UIUtil
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.launch

/**
* Action to toggle work break
*/
class ToggleWorkBreakAction : AnAction("Begin Break", "Take a break from work", AllIcons.Actions.Pause) {

init {
ApplicationManager.getApplication().messageBus.connect()
.subscribe(
WorkBreakStateChangeNotifier.WORK_BREAK_STATE_CHANGE_TOPIC,
WorkBreakStateChangeNotifier { _, _ ->
UIUtil.invokeLaterIfNeeded {
update(AnActionEvent.createFromAnAction(
this,
null,
"",
DataContext.EMPTY_CONTEXT
))
}
})
}
override fun update(e: AnActionEvent) {
if (WorkBreakState.isOngoing().not()) {
e.presentation.text = "Begin Break"
e.presentation.description = "Take a break from work."
} else {
e.presentation.text = "Stop Break"
e.presentation.description = "Stop the ongoing break session."
}
}

override fun getActionUpdateThread(): ActionUpdateThread {
return ActionUpdateThread.EDT
}

private val stopWorkBreakCoroutineScope = CoroutineScope(Dispatchers.IO)

override fun actionPerformed(e: AnActionEvent) {
if (WorkBreakState.isOngoing().not()) {
StartWorkBreakDialog().show()
} else {
stopWorkBreakCoroutineScope.launch {
WorkBreakState.instance.processing = true
service<WorkBreakService>().stopWorkBreak().let {
WorkBreakState.instance.currentBreak = null
}
WorkBreakState.instance.processing = false
}
}
}
}
Loading

0 comments on commit d1f4595

Please sign in to comment.