@@ -11,6 +11,7 @@ import Control.Monad.Catch (Exception (displayException), MonadThrow, throwM, tr
1111import Control.Monad.IO.Class (liftIO)
1212import Data.Bits
1313import Data.Default
14+import Data.List (isSuffixOf)
1415import qualified Data.Map as Map
1516import Data.Maybe
1617import qualified Data.Text as T
@@ -19,7 +20,7 @@ import System.Directory
1920import System.Environment (getEnvironment)
2021import System.FilePath
2122import System.Posix.Files
22−import System.Process (delegate_ctlc, env, proc)
23+import System.Process (delegate_ctlc, env, proc, readCreateProcess, cwd)
2324import Text.URI (URI)
2425import qualified Text.URI as URI
2526import Text.URI.Lens
@@ -156,9 +157,45 @@ deployMobile platform mobileArgs = withProjectRoot "." $ \root -> do
156157 let srcDir = root </> "src"
157158 exists <- liftIO $ doesDirectoryExist srcDir
158159 unless exists $ failWith "ob test should be run inside of a deploy directory"
160+ when (platform == "android") $ do
161+ let keystorePath = root </> "android_keystore.jks"
162+ hasKeystore <- liftIO $ doesFileExist keystorePath
163+ when (not hasKeystore) $ do
164+ -- TODO log instructions for how to modify the keystore
165+ putLog Notice $ "Creating keystore: " <> T.pack keystorePath
166+ createKeystore root $ KeytoolConfig
167+ { _keytoolConfig_keystore = keystorePath
168+ , _keytoolConfig_alias = "obelisk"
169+ , _keytoolConfig_storepass = "obelisk"
170+ , _keytoolConfig_dname = "CN=mqttserver.ibm.com, OU=ID, O=IBM, L=Hursley, S=Hants, C=GB" -- TODO Read these from config?
171+ }
159172 result <- nixBuildAttrWithCache srcDir $ platform <> ".frontend"
160173 callProcessAndLogOutput (Notice, Error) $ proc (result </> "bin" </> "deploy") mobileArgs
161174
175+data KeytoolConfig = KeytoolConfig
176+ { _keytoolConfig_keystore :: FilePath
177+ , _keytoolConfig_alias :: String
178+ , _keytoolConfig_storepass :: String
179+ , _keytoolConfig_dname :: String
180+ } deriving (Show)
181+
182+createKeystore :: MonadObelisk m => FilePath -> KeytoolConfig -> m ()
183+createKeystore root config = do
184+ let expr = "with (import " <> toImplDir root <> ").reflex-platform.nixpkgs; pkgs.mkShell { buildInputs = [ pkgs.jdk ]; }"
185+ callProcessAndLogOutput (Notice,Notice) $ (proc "nix-shell" ["-E" , expr, "--run" , keytoolCmd]) { cwd = Just root }
186+ where
187+ keytoolCmd = unwords $ "keytool" :
188+ [ "-genkeypair -noprompt"
189+ , "-keystore", _keytoolConfig_keystore config
190+ , "-keyalg RSA -keysize 2048 -validity 10000"
191+ , "-storetype pkcs12"
192+ , "-storepass", _keytoolConfig_storepass config
193+ , "-alias", _keytoolConfig_alias config
194+ , "-dname ", quote $ _keytoolConfig_dname config
195+ ]
196+ quote x = "\"" <> x <> "\""
197+
198+
162199-- | Simplified deployment configuration mechanism. At one point we may revisit this.
163200writeDeployConfig :: MonadObelisk m => FilePath -> FilePath -> String -> m ()
164201writeDeployConfig deployDir fname = liftIO . writeFile (deployDir </> fname)