Arhive kategorija: Uncategorized

Python Meet #3

Evo nam još jednog okupljanja Pythonaša i onih koji bi to željeli postati. Python meet #3 će se održati u ponedjeljak, 21. 11. 2011., u KSET-u, Unska 3.

Predgrupa (poznata britanska komičarska grupa) kreće s nastupom u 16 sati, dok će sam meet započeti u 18 sati.

Više informacija o meetu pročitajte na KSET-ovim stranicama.

Vidimo se u ponjedjeljak!

Freelancer računica

CC-BY AMagill @ Flickr

Nakon nedavnog prilično čitanog članka u Globusu o online/web freelancingu moglo se čuti i pročitati dosta komentara o masnim parama koje se mlate u online-biznisu, nakon kojih bi čovjek dobio dojam da je taj internet biznis jako lukrativna i tajanstvena prilika u koju su rijetki upućeni nekako ušli i sad se kupaju u zlatu.

Pritom se ponekad zaboravlja da prihodi i neto dohodak nisu ista stvar i financijsku realnost unutar koje freelanceri, kao i svi ostali poduzetnici, moraju poslovati. U nadi da će nekom biti informativna ili korisna, složio sam okvirnu računicu koju bi mogao imati neki hipotetski freelancer. Prilikom računanja zaokruživao sam i procjenivao vrijednosti na neki “prosjek” – pojedini brojevi razlikuju se prilično od slučaja do slučaja, ali recimo da su redovi veličine tu negdje.

Katica za sve

Recimo da se potaknuti člankom želite baciti u freelancing. Web developer ste (možda designer / front end developer, možda backend / php / sql ninja); kod (programerski ili markup) štrikate već godinama, stvarno ste dobri u onom što radite i imate već nekoliko fuševa iza sebe.

Naravno, osim samog “odrađivanja posla” morat ćete se baviti i sa promocijom (bilo običnim reklamiranjem, bilo pisanjem vlastitog bloga kojim dižete svoj osobni brand), networkingom (sakupljanjem i održavanjem kontakata, odlascima na konferencije, itd), prodajom svojih proizvoda ili usluga (tj. trebate nagovoriti nekog da upravo vama plati – samo zato što nešto znate ne znači automatski da će korisnik vas odabrati), te naposlijetku i pružanjem korisničke podrške.

A pošto sve ovo zajedno ne želite raditi u fušu nego iz toga stvoriti normalan posao, morati ćete se baviti i papirologijom vezanom uz rad tvrtke koju otvorite. Dio te papirologije možete prepustiti knjigovodstvenim i drugim servisima, ali dio će ostati vaša briga.

Dakle, za početak, poželjno je da imate iskustvo ne samo u Web razvoju, nego i u vođenju projekata, prodaji, oglašavanju, a hodanje po kancelarijama i kupovanje biljega vam ne bi smjelo biti previše frustrirajuće.

Minus i plus

Recimo da procjenjujete da će vaši mjesečni prihodi (dakle, količina novaca koji vam klijenti plate, minus PDV domaćih klijenata) biti oko 16 tisuća kuna. Uzimam ovu brojku jer je bila navedena u Globusovom članku – doduše kao “plaća”, ali dosta ljudi nije vjerovalo u taj “ogromni” iznos, pa uzmimo je kao razumnu (uspješnu) brojku u ovoj računici.

Minimalni mjesečni troškovi na koje možete računati su vam mobitel (recimo 200kn), internet i druge režije vezane uz poslovanje (200kn), troškovi prijevoza (iako radite iz spavaće sobe, još uvijek morate na poneki sastanak, poslovnu kavu ili odnijeti papire u Finu – ako radite u nekoj normalnoj firmi, troškove ovoga vam pokriva poslodavac) u npr. visini mjesečne ZETove karte (~240kn), topli obrok (kojeg vam u nekoj firmi pokriva poslodavac) od recimo 500kn mjesečno, te recimo 100kn za pokrivanje netbanking i sličnih troškova.

Trebate imati i opremu na kojoj ćete raditi – minimalno nekakvo računalo, ali vjerojatno i nekakav backup disk, veći monitor, i slično. Recimo da ćete godišnje na računala, mobitel i raznoraznu uredsku opremu potrošiti 10 tisuća kuna (što ispada 830kn mjesečno). Osim toga morat ćete si nabaviti nekakvu stručnu literaturu, zakupiti server ili prostor na serveru, kupiti domenu ili dvije, eventualno se negdje reklamirati ili odlaziti na konferencije kako bi ostali relevantni u vašoj branši. Recimo da na godišnjoj razini još na to potrošite 6000kn, odnosno, svedeno na mjesečni iznos, 500kn mjesečno.

U malo preglednijem tabularnom prikazu, to izgleda ovako:

Opis Iznos (kn/mj)
Primanja (prihodi) 16.000
Mobitel 200
Internet, režije 200
Prijevoz 240
Topli obrok 500
Netbanking i slični troškovi 100
Računalo i oprema za rad 830
Literatura, konferencije, zakup servera, domene, itd 500
Troškovi (rashodi) 2.570
Ukupno dobit 13.430

Ovdje opisani mjesečni troškovi su vrlo općenite procjene, ali malo je vjerojatno da ćete u praksi imati niže troškove. Ovi iznosi predstavljaju dobru početnu brojku za freelancera koji skromno živi, ne ide na konferencije na druge kontinente, kupuje softver sa popustom ili koristi free software, i ne luduje za najnovijim gadgetima.

Nadopuna: par ljudi me pitalo o troškovima vezanima uz vođenje knjiga (koje sam namjeravao također uvrstiti ovdje, ali sam zaboravio – isprika na propustu). Mislim da se svakako isplati to outsourceati knjigovodstvu i prepustiti im brigu o tome koji je trenutno zakon i porez na snazi i u kom trenu kako treba što knjižiti. To zadovoljstvo će vas stajati 500 – 1000kn. Pretpostavimo da je 500kn + PDV mjesečno, što vam u konačnici smanji mjesečnu plaću “na ruke” za oko 200-300 kn.

Bruto, Neto & još jedan Bruto

U daljnoj računici stvari se malo kompliciraju. Spomenuta dobit je ono što vam ostane u tvrtki nakon plaćanja troškova, ali to nije vaša plaća. Ukoliko ste obrtnik, ili ukoliko imate d.o.o. i jednostavno si želite cijeli iznos isplatiti kroz plaću, navedena dobit vam je zapravo takozvani bruto2. To je onaj iznos kojeg radnici nikad ne gledaju a zapravo predstavlja trošak poslodavca.

Mala digresija: neto plaća je ono što dobijemo “na ruke” (ili na tekući). Bruto (ili bruto1) plaća je zapravo naša plaća koju nam isplaćuje poslodavac, a iz nje mi osobno plaćamo porez, prirez te izdvajamo za mirovinu (papirologiju poslodavac obavlja umjesto nas, ali novci kojima se plaća su još uvijek naši). Na bruto1 poslodavac još plaća zdravstveno osiguranje za nas i još neka davanja, a taj ukupni iznos zove se bruto2 i predstavlja ukupni trošak radnika za poslodavca. Detaljniji opis bruto1 i bruto2 sa točnim postocima možete naći na Moj Posao portalu.

(Ukoliko ste obrtnik stvari se malo drugačije računaju, jer su davanja fiksna za godinu dana, i nešto niža nego što bi bila davanja iz bruto1. Ali, pošto cijeli račun radimo sa otprilike procjenjenim brojevima, i ovo pojednostavljenje će poslužiti).

Kalkulatorom za izračun plaće sa Moj Posao iz cca 13400kn bruto2 dobijamo otprilike 7500 kn neto plaću.

Dakle početnih 16 tisuća srezali smo na 7500, nešto manje od 47% originalnog iznosa. Ostatak su porezi i davanja državi (nešto manje od 37%) te oko 16% za troškove poslovanja.

Ukoliko namjeravate osnovati d.o.o, jedna legalna opcija je isplatiti jedan dio preko normalne plaće, a drugi isplatiti kao dobit doo-a (na što se plaća porez na dobit od 20%). Naravno, problem sa ovim je da si smanjujete i davanja za mirovinsko osiguranje, što vam u dalekoj budućnosti znači manju mirovinu. Doduše, većina poduzetnika koja znam radije bira cash sada nego obećanje da će imati mirovinu za 40tak godina.

Recimo da vas nije briga za vašu mirovinu jednog dana i odlučite biti na minimalcu a ostatak dobiti preuzimati kao dobit. Neto plaća će vam biti oko 2500kn, bruto2 oko 3500kn, a preostali iznos si isplatite kao dobit, od čega oko 7500kn ide vama a oko 2500 državi. Na ovaj način ukupno mjesečno dobijete 10000 kn (oko 62% prihoda), državi ide oko 22%, a na troškove poslovanja opet 16%.

Vel’ke pare?

Dakle, kao skromni, marljivi i uspješni freelancer sa oko 16 tisuća kuna prihoda mjesečno, možete očekivati između 7.5 i 10 tisuća kuna “na ruke”. Nisu mali novci, pogotovo za zemlju u kojoj velik broj ljudi radi na (skoro) minimalcu ili uopće nema posao, ali nisu ni nekakvi ogromni neobjašnjivi iznosi koje ista osoba sa istim znanjem, sposobnostima i iskustvom ne bi mogla dobiti i u dobrim domaćim tvrtkama.

Preporuka: nekoliko filmskih mozgalica

Kao mali odmak od inače tehnoloških tema o kojima pišem, evo nekoliko filmskih preporuka od mene: filmovi koji se bave umom i zagonetkama koje on skriva. Neki od filmova su poznati blockbusteri koji su nedavno prikazivani u kinima (ili se još prikazuju), poput “Početka”, dok su mi drugi bili sasvim nepoznati i slučajno sam na njih naletio, obično u see also dijelu recenzije poznatijih filmova.

Listu sam poredao po subjektivnoj procjeni koliko mi je film “čudan”, tj. nekonvencionalnij ili traži veći angažman malih sivih stanica da bi se uživalo u njemu.

Shutter Island

US marshall dolazi na otok Shutter, istražiti slučaj osobe pobjegle iz bolnice/zatvora za mentalno bolesne kriminalce. (IMDB, YouTube).

Memento

Čovjek koji je izgubio mogućnost stvaranja novih pamćenja uz pomoć tetovaža i fotografija traga za ubojicom svoje supruge. (IMDB, YouTube).

The Machinist

Čovjek koji već godinu dana pati od nesanice počinje gubiti razum. (IMDB, YouTube).

Inception

High-tech kradljivac informacija koji provaljuje u tuđe snove treba odraditi svoj zadnji posao: usaditi ideju u nečiju podsvjest. (IMDB, YouTube).

Mr. Nobody

Tko je Nemo Nobody? (IMDB, YouTube).

Ako znate za još koji dobar film u sličnom stilu, svakako javite u komentarima.

PS. Ako vam filmovi s ovog popisa nisu dovoljno mind-bending, preporučam pogledati The Fountain (YouTube). Nisam ga stavio na popis jer mi nije dobar poput gorenavedenih, a i nije čisto mind-related).

Razvoj za Android (većinom) iz shella

Dobričin zanimljiv post o komandnoj liniji na Androidu potaknuo me da opišem svoj Android dev setup. (Update: moj setup je na Linux sustavu, iako vjerujem da su koraci slični ili isti i za OS X ili Windows platforme – jedina razlika je u shellu koji koristite i načinu na koji postavljate path)

Vjerojatno većina programera koji razvijaju za Android (ili su bar skinuli SDK i malo gledaju o čemu se tu radi) koriste Eclipse kao razvojno okruženje. Uostalom, Eclipse je i preporučen način razvoja za Android. No kako stvarno ne volim ovaj alat, pri svom radu radije koristim (većinom) komandnolinijske alternative. Na moju sreću, Google nije zanemario i nas koji ne volimo Eclipse, nego nam je osigurao solidan set alata s kojima možemo (gotovo) sve što je moguće i sa Eclipseom.

Uz pretpostavku da je Android SDK instaliran u /opt/android-sdk, pokušajmo kreirati, isprogramirati i deployati “Hello World” aplikaciju. Prvo ćemo podesiti path tako da možemo jednostavno pozivati SDK alate:

> export PATH=/opt/android-sdk

Prvi alat koji nam je potreban se zove android, koji nam koristi za kreiranje naših projekata, konfiguriranje emulatora, nadogradnju projekatata kod nadogradnje SDK-a. Ovaj program ima i GUI i komandnolinijsku varijantu – GUI varijanta je nešto očitija (pogotovo kod kreiranja i konfiguriranja emulatora, odnosno Android Virtual Devicea), no mi ćemo se zasad zadržati na komadnoj liniji.

Pogledajmo prvo koje verzije Androida možemo targetirati:

> android list targets

Ovim ćemo dobiti popis verzija za koje možemo razvijati našu aplikaciju – primjerice, Android 2.1 ovdje ima oznaku “android-7″. Sa ovom informacijom možemo kreirati naš novi projekt:

> android create project --target android-7 \
            --name HelloWorldProject \
            --path moji-projekti/HelloWorldProject \
            --activity Main
            --package hr.primjer.mojprojekt

Alat će kreirati potrebne direktorije i popuniti ih potrebnim stvarima, tako da mi možemo odmah otvoriti novostvorenu moji-projekti/HelloWorldProject/src/hr/primjer/mojprojekt/Main.java i editirati activity naše aplikacije.

Nakon što napravimo promjene, možemo buildati cijeli projekt, za početak u debug modu, koristeći ant, vrlo popularan build tool za Java projekte općenito (svu potrebnu konfiguraciju generirao je prethodni poziv android alata):

> cd moji-projekti/HelloWorldProject
> ant debug

Ukoliko nije bilo grešaka prilikom kompajliranja, trebali bi na kraju dobiti poruku BUILD SUCCESSFUL. Yay! Sada možemo i isprobati kako naša aplikacija radi. Ali prije toga, morat ćemo kreirati i konfigurirati emulator. Naime, Android SDK omogućuje korištenje više emulatora uređaja što je korisno za isprobavanje na različitim hardverskim karakteristikama (npr veličine ekrana, memorija, različiti senzori i slično).

Kako bi kreirali AVD odnosno emulator, najjednostavnije je pokrenuti android bez ikakvih argumenata, čime će se pokrenuti GUI sučelje za konfiguraicju AVD-ova. (Stvar se može i preko komandne linije, ali tko će popamtiti sve switcheve za to).

Kada imamo jedan ili više AVDova kreiranih, možemo ih na brzaka izlistati sa android list avd, a potom i pokrenuti željeni emulator (ili više njih):

> emulator -avd ImeAVDUređaja

Osim samog emulatora, korisna stvar je i Dalvik Debug Monitor (ddms), standalone GUI alat koji omogućuje pregledavanje trace logova, očitanje stanja uređaja, ili emulatora, uzimanje screenshota i slično. Neke od ovih stvari dostupne su i izravno iz komandne linije (za potpun popis upišite samo adb što će vam prikazati pomoć):

> adb devices # lista spojenih uređaja
> adb logcat # ispis trace logova
> adb emu <cmd> # zadavanje naredbe emulatoru
> adb shell # remote shell na emulator ili uređaj

Nakon što smo napravili debug build naše aplikacije, i pokrenuli emulator, trebamo aplikaciju “instalirati” u emulator kako bi je mogli isprobati:

> adb install -r bin/HelloWorldProject-debug.apk

Opcija -r znači “reinstall” i govori adbu da, ukoliko aplikacija već postoji na uređaju, makne postojeću i instalira je nanovo (korisnički podaci pritom ostaju netaknuti).

Ukoliko imate istovremeno pokrenut emulator i spojen uređaj, opcijama -e (emulator) ili -d (device) određujete kamo želite poslati instalaciju. U slučaju da istovremeno imate spojeno nekoliko emulatora ili uređaja, opcijom -s možete točno odrediti cilj naredbe (argument za -s je ID emulatora kojeg možete saznati sa adb devices).. Sve tri opcije vrijede za većinu adb naredbi, ne samo za install.

Nakon što je aplikacija dovršena i prošla je testiranje u emulatorima i na testnim uređajima, potrebno je napraviti release paket, koji možemo distribuirati korisnicima naše aplikacije. Prilikom izrade release paketa, potrebno ga je potpisati našim developerskim ključem (koji, ukoliko aplikaciju distribuirate na Market, mora biti također prijavljen na Android Marketu). Developerski ključ možete sami kreirati alatom keytool, a više o tome možete pročitati na Android Dev Guide stranicama. Procedura je zapravo ista i za Eclipse korisnike i za ostale, osim što ako ne koristite eclipse, putanju do keystorea je potrebno ručno dodati u build.properties datoteku unutar vašeg projekta.

Sam postupak buildanja u release modu i potpisivanja je jednostavan:

> ant release

…nakon čega dobijate bin/HelloWorldProject-release.apk datoteku koju možete instalirati na uređaje, uploadati na Market ili distribuirati na neki drugi način.

Git početnica, 4. dio – rješavanje konflikata

U prošlom postu u Git serijalu spomenuli smo mogućnost konflikata prilikom rebaziranja ili spajanja grana te dali par sugestija kako ih izbjeći. No kod kompliciranijih projekata i workflowova konflikti su ponekad neizbježni, stoga je korisno znati kako riješiti konflikt kad do njega dođe.

Rješavanje konflikata

Ukoliko sami radite na projektu, konflikti vam se vjerojatno neće događati (osim ukoliko ne pazite). No, ukoliko radite na projektu sa više ljudi, može vam se zadesiti da se nađete u situaciji gdje ćete morati riješiti konflikt.

Recimo da je naš helloworld projekt dobio na važnosti i sada na njemu rade dva developera, Mirko i Slavko. Mirko i Slavko u stvarnom životu radit će na svojim granama u svojim klonovima repozitorija, ali da si ovdje pojednostavnimo priču, svaki će imati po jednu granu u našem zajedničkom repozitoriju.

Kreirajmo obje grane, bez prebacivanja u njih:

> git checkout master
Switched to branch 'master'

> git branch mirko
> git branch slavko
> git branch -l
  helloworld-0
* master
  mirko
  slavko

Dolazi Mirko, vidi problem u načinu kako je definirana funkcija main i popravlja ga u svojoj grani:

> git checkout mirko
Switched to branch 'mirko'

[...promjene hello.c...]

> git diff
diff --git a/hello.c b/hello.c
index 0bb4941..8b08068 100644
--- a/hello.c
+++ b/hello.c
@@ -1,6 +1,7 @@
 #include <stdio.h>

-int main(void)
+int
+main(int argc, char *argv[])
 {
   printf("Hello world\n");
   return 0;

> git commit -a -m "popravio main prototip"
[mirko 4e5f904] popravio main prototip
 1 files changed, 2 insertions(+), 1 deletions(-)

U međuvremenu, dolazi Slavko, vidi isti problem, ne zna da je Mirko radio na istoj stvari pa ga rješava kod sebe:

> git checkout slavko
Switched to branch 'slavko'

[...promjene hello.c...]

> git diff
diff --git a/hello.c b/hello.c
index 0bb4941..38586b0 100644
--- a/hello.c
+++ b/hello.c
@@ -1,6 +1,6 @@
 #include <stdio.h>

-int main(void)
+int main(int argc, char **argv)
 {
   printf("Hello world\n");
   return 0;

> git commit -a -m "prepravio definiciju funkcije main"
[slavko 4bb59be] prepravio definiciju funkcije main
 1 files changed, 1 insertions(+), 1 deletions(-)

Sve je dobro dok su promjene u zasebnim granama. No u jednom trenu ćemo željeti sve Mirkove i Slavkove promjene spojiti u master. Prva promjena će proći dobro, no na drugoj će nam se dogoditi konflikt.

> git checkout master
Switched to branch 'master'

> git merge mirko
git merge mirko
Updating 302ef80..4e5f904
Fast-forward
 hello.c |    3 ++-
 1 files changed, 2 insertions(+), 1 deletions(-)

> git merge slavko
git merge slavko
Auto-merging hello.c
CONFLICT (content): Merge conflict in hello.c
Automatic merge failed; fix conflicts and then commit the result.

Uh, huh… obojica su mijenjala isto mjesto u istoj datoteci, i git ne zna kako riješiti problem. Zbog toga je merge pauziran i dana nam je prilika da riješimo konflikt. Pogledajmo što se dogodilo:

git diff
diff --cc hello.c
index 8b08068,38586b0..0000000
--- a/hello.c
+++ b/hello.c
@@@ -1,7 -1,6 +1,11 @@@
  #include <stdio.h>

++<<<<<<< HEAD
 +int
 +main(int argc, char *argv[])
++=======
+ int main(int argc, char **argv)
++>>>>>>> slavko
  {
    printf("Hello world\n");
    return 0;

> cat hello.c
#include <stdio.h>

<<<<<<< HEAD
int
main(int argc, char *argv[])
=======
int main(int argc, char **argv)
>>>>>>> slavko
{
  printf("Hello world\n");
  return 0;
}

Diff prikazuje obje nekompatibilne promjene. Prva je iz trenutne grane (odnosno to je ona Mirkova promjena koju smo uspješno preuzeli spajanjem Mirkove grane), dok je druga iz grane slavko. Rješimo konflikt modificiranjem tog dijela datoteke da izgleda onako kako mi želimo:

[...promjene hello.c...]
cat hello.c
#include <stdio.h>

int
main(int argc, char **argv)
{
  printf("Hello world\n");
  return 0;
}

> git diff
diff --cc hello.c
index 8b08068,38586b0..0000000
--- a/hello.c
+++ b/hello.c
@@@ -1,7 -1,6 +1,7 @@@
  #include <<tdio.h>

 -int main(int argc, char **argv)
 +int
- main(int argc, char *argv[])
++main(int argc, char **argv)
  {
    printf("Hello world\n");
    return 0;

> git add hello.c
> git commit
[master fd96bab] Merge branch 'slavko'

Diff prikaz u slučaju konflikata je pomalo zbunjujuć, no snalaženje u samoj datoteci koju treba popraviti je relativno jednostavno - konflikt je između <<<<<<< i >>>>>>>, a ======= razdvaja konfliktne promjene.

Konflikt prilikom rebaziranja

Kao što smo već prije vidjeli, obično želimo grane održavati tako da u svakom trenu njihove promjene budu primjenjive na master (odnosno na baznu granu gdje ih na kraju želimo spojiti), a jedan od razloga je upravo izbjegavanje konflikata kod spajanja.

Jedan od razloga zbog kojih je konflikt kod spajanja nezgodan je i činjenica da problem praktički "prebacujemo" onom tko radi merge, a kod većih projekata to je obično osoba koja održava projekt (tj. glavni developer). Ukoliko od nje tražite da granu sa vašim promjenama spaja sa masterom, a to izaziva konflikte kod mergea, zapravo ste prilično nepristojni.

Zato je bolje prije nego zatražite (ili krenete raditi) spajanje rebazirati svoju granu tako da samo spajanje bude čisto. To znači da ćete eventualne konflikte morati sami rješiti prilikom rebaziranja.

Vratimo se malo u prošlost i zaboravimo da smo radili merge Mirkove i Slavkove grane:

> git reset --hard 302ef80039bd55fbbc680d84e37e5ebcf7f63a5c
HEAD is now at 302ef80 dodan README

Mirko odluči spojiti svoju granu s masterom. Njegovu granu nije potrebno rebazirati jer se nastavlja na master (tj master nema nikakvih novih promjena):

> git merge mirko
Updating 302ef80..4e5f904
Fast-forward
 hello.c |    3 ++-
 1 files changed, 2 insertions(+), 1 deletions(-)

Slavko odluči spojiti svoju granu. Njegovu granu je potrebno rebazirati jer
master ima novih comittova:

> git checkout slavko
Switched to branch 'slavko'

> git rebase master
First, rewinding head to replay your work on top of it...
Applying: prepravio definiciju funkcije main
Using index info to reconstruct a base tree...
Falling back to patching base and 3-way merge...
Auto-merging hello.c
CONFLICT (content): Merge conflict in hello.c
Failed to merge in the changes.
Patch failed at 0001 prepravio definiciju funkcije main

When you have resolved this problem run "git rebase --continue".
If you would prefer to skip this patch, instead run "git rebase --skip".
To restore the original branch and stop rebasing run "git rebase --abort".

Ovo izgleda mnogo strašnije nego poruka kod mergea! Ali problem je isti, u što se možemo uvjeriti pomoću git diff (s tim da će umjesto imena naše grane biti naziv commita u našoj grani s kojim ima problema). Nakon što napravimo ispravke u datoteci, trebamo nastaviti proces rebaziranja:

[...promjene hello.c...]
> git add hello.c
> git rebase --continue
Applying: prepravio definiciju funkcije main

Ovdje nismo ručno radili git commit, nego smo nakon popravka nastavili proces rebaziranja. Kako rebaziranje ide commit po commit, ukoliko ima još konflikata u narednim commitovima, rebase bi se opet zaustavio i zatražio da popravimo stvari.

Ukoliko zaključimo da je commit nepotreban (npr. zato što je u drugoj grani taj problem već riješen), možemo ga odbaciti. Ako se radi o ozbiljnom problemu za kojeg ne znamo kako ga riješiti, možemo prekinuti rebase, a grana će nam se vratiti u prvobitno stanje. U tom slučaju ćemo vjerojatno morati rješavati merge konflikte prilikom spajanja i napraviti merge a ne rebase.